Разработка и Конфигурация · 10 мин
Как получить целое число в запросе 1С
Как получить целое число в запросе 1С: функция Целое(), приведение типов через Выразить, округление и отброс дробной части. Примеры кода и типичные ошибки.
При построении запросов в 1С часто требуется отбросить дробную часть числа — например, при расчёте количества упаковок, целых дней между датами или номера интервала. Язык запросов 1С не содержит привычных функций округления из встроенного языка, поэтому задачу решают несколькими обходными приёмами: функцией Целое(), приведением типа через ВЫРАЗИТЬ, арифметическими преобразованиями и функциями дат.
Выбор способа зависит от того, что именно нужно: просто отбросить дробную часть, округлить по математическим правилам или получить целое число заданной разрядности с контролем типа результата. Ниже разобраны все рабочие варианты с примерами кода, ограничениями и типичными ошибками.
Функция Целое(): основной способ отбросить дробную часть
В современных версиях платформы 1С:Предприятие в языке запросов доступна функция Целое(). Она принимает числовое выражение и возвращает целую часть, просто отбрасывая дробную составляющую без округления. Это самый простой и читаемый способ получить целое число прямо в тексте запроса.
ВЫБРАТЬ
Целое(Товары.Количество / 12) КАК КоличествоУпаковок
ИЗ
Документ.РеализацияТоваровУслуг.Товары КАК Товары
Важно понимать семантику: Целое(7.9) вернёт 7, а не 8. Функция не округляет, а усечёт число. Для положительных значений это эквивалент округления вниз, но для отрицательных чисел результат отличается от математического пола: Целое(-2.7) даст -2, а не -3. Если в данных возможны отрицательные значения (сторно, корректировки, возвраты), это поведение нужно учитывать явно.
Функция доступна не во всех версиях платформы. Если конфигурация работает на старой платформе и запрос с Целое() падает с ошибкой «функция не обнаружена», используйте приёмы из разделов ниже — они работают в любой версии.
Приведение типа через ВЫРАЗИТЬ с нулевой точностью
Второй рабочий способ — оператор ВЫРАЗИТЬ с явным указанием типа Число(N, 0). При приведении числа к типу с нулевой точностью платформа выполняет округление по математическим правилам: 7.4 превратится в 7, а 7.5 — в 8.
ВЫБРАТЬ
ВЫРАЗИТЬ(Товары.Сумма / Товары.Количество КАК Число(15, 0)) КАК ЦенаЦелая
ИЗ
Документ.РеализацияТоваровУслуг.Товары КАК Товары
Этот приём одновременно решает две задачи: округляет значение и фиксирует тип поля результата запроса. Это полезно, когда поле дальше участвует в соединениях, группировках или выгружается в таблицу значений — тип будет гарантированно числовым с заданной разрядностью, без сюрпризов с составными типами.
Ограничение способа — риск переполнения разрядности. Если указать Число(5, 0), а в данных встретится значение больше 99999, запрос завершится с ошибкой преобразования. Всегда закладывайте разрядность с запасом относительно максимально возможного значения в источнике.
Арифметические приёмы для старых платформ
Если функция Целое() недоступна, а поведение ВЫРАЗИТЬ с округлением не подходит, целую часть получают арифметически. Классический приём: вычесть из числа остаток от деления на единицу. Однако в языке запросов нет функции остатка от деления, поэтому на практике чаще используют комбинацию с ВЫРАЗИТЬ и поправкой на округление:
ВЫБРАТЬ
ВЫБОР
КОГДА Число - ВЫРАЗИТЬ(Число КАК Число(15, 0)) > 0.5
ТОГДА ВЫРАЗИТЬ(Число КАК Число(15, 0)) - 1
ИНАЧЕ ВЫРАЗИТЬ(Число КАК Число(15, 0))
КОНЕЦ КАК ЦелаяЧасть
Другой распространённый приём — вычисление целого через разность с половиной для округления вверх: ВЫРАЗИТЬ(Число + 0.5 КАК Число(15, 0)) даёт округление к ближайшему целому для положительных чисел. Для округления вверх (потолок) при положительных значениях используют ВЫРАЗИТЬ(Число - 0.5 КАК Число(15, 0)) + 1.
Такие конструкции труднее читать, поэтому снабжайте их комментариями в тексте запроса. Если подобная логика встречается в нескольких запросах, рассмотрите перенос расчёта во временную таблицу или в код модуля, где доступны Цел() и Окр() встроенного языка.
Целые числа из дат: РазностьДат и функции периодов
Частный, но очень частый сценарий — получить целое количество дней, месяцев или лет между датами. Для этого предназначена функция РАЗНОСТЬДАТ, которая уже возвращает целое число:
ВЫБРАТЬ
РАЗНОСТЬДАТ(Заказы.ДатаЗаказа, Заказы.ДатаОтгрузки, ДЕНЬ) КАК ДнейДоставки
ИЗ
Документ.ЗаказПокупателя КАК Заказы
Функция считает количество полностью прошедших единиц указанного типа. Разность в один день и двадцать три часа при типе ДЕНЬ даст 0, а не 1 — это стандартное поведение, которое нужно учитывать при расчётах сроков. Если требуется «календарная» разница с учётом неполных суток, добавьте к результату проверку остатка через РАЗНОСТЬДАТ(..., ЧАС) или СЕКУНДА.
Для получения целых номеров периодов используйте функции ГОД(), МЕСЯЦ(), ДЕНЬ(), ЧАС(), НЕДЕЛЯ() — все они возвращают целые числа и часто применяются для группировок и нумерации интервалов в отчётах.
Сравнение способов
Отбрасывает дробную часть без округления. Простой и читаемый, но недоступен на старых платформах.
Округляет по математическим правилам и фиксирует тип поля. Требует запаса разрядности, иначе ошибка переполнения.
Полный контроль над правилом округления, работает везде. Минус — громоздкий и трудночитаемый текст запроса.
Только для дат: возвращает целое число полных периодов. Не заменяет округление обычных чисел.
Целое число в СКД и динамических списках
В схеме компоновки данных те же функции языка запросов доступны и в выражениях вычисляемых полей, если поле вычисляется на уровне запроса. Добавьте вычисляемое поле с выражением Целое(Количество / НормаУпаковки) и используйте его в настройках отчёта как обычный ресурс или измерение.
Если вычисление выполняется на языке выражений СКД (а не в запросе), доступны функции встроенного языка, включая Цел() и Окр(). Различайте эти два контекста: синтаксис запроса проверяется конструктором запроса, а выражения СКД — при формировании отчёта, и ошибка в одном месте не всегда очевидна при редактировании другого.
В динамических списках с произвольным запросом функции работают так же, но помните: вычисляемые поля с преобразованиями не индексируются, и отбор по ним будет выполняться полным сканированием. На больших таблицах лучше отбирать по исходному полю, а целое значение выводить только в представление.
Проверка результата и типичные ошибки
После добавления преобразования проверьте результат на граничных значениях: 0, 0.5, -0.5, большие числа, NULL. Значение NULL в числовом поле приведёт к NULL в результате любой из перечисленных функций — если это нежелательно, оберните выражение в ЕСТЬNULL(Поле, 0) до преобразования.
Отдельная ошибка — ожидание, что тип поля результата автоматически станет целым. Функция Целое() возвращает число, но точность и разрядность поля в выгрузке определяются платформой; если тип критичен для дальнейшей обработки, зафиксируйте его явно через ВЫРАЗИТЬ.
Как проверить результат
7 при усечении, 8 при округлении — соответствует выбранному способу
Неожиданное значение или NULL
Осознанный результат: -2 для Целое() или -3 для округления вниз
Знак или модуль не соответствуют ожиданию
0 или явно заданное значение по умолчанию
NULL попадает в итоги и группировки
Укладывается в разрядность Число(N, 0)
Ошибка преобразования при выполнении запроса
Когда перенести расчёт из запроса в код
Не всякую задачу стоит решать в запросе. Если требуется сложное округление (банковское, с учётом знака, с несколькими правилами), логика прозрачнее во встроенном языке: выгрузите результат запроса и обработайте его функциями Цел() и Окр() в цикле или через ЗначениеВСтрокуВнутр-независимые преобразования колонок.
Правило выбора простое: если преобразование нужно для группировки, соединения или отбора внутри запроса — делайте его в запросе. Если оно нужно только для отображения или разовой обработки результата — выполняйте в коде, где доступны полноценные математические функции и понятная отладка.
Как выбрать действие
Частые вопросы
Чем Целое() в запросе отличается от Цел() во встроенном языке?
По смыслу обе функции отбрасывают дробную часть. Разница в контексте: Целое() выполняется на сервере СУБД внутри запроса, а Цел() — в коде 1С после получения данных. Поведение на отрицательных числах у обеих одинаковое: усечение к нулю.
Как округлить число в большую сторону в запросе 1С?
Для положительных чисел используйте ВЫРАЗИТЬ(Число - 0.5 КАК Число(15, 0)) + 1. Если платформа поддерживает Целое(), альтернатива — Целое(Число) + ВЫБОР КОГДА Число - Целое(Число) > 0 ТОГДА 1 ИНАЧЕ 0 КОНЕЦ.
Почему запрос с ВЫРАЗИТЬ падает с ошибкой преобразования?
Чаще всего значение не помещается в указанную разрядность: например, число 123456 в тип Число(5, 0). Увеличьте разрядность с запасом или предварительно отфильтруйте слишком большие значения.
Как получить целое от деления без остатка?
Используйте Целое(Делимое / Делитель) или ВЫРАЗИТЬ(Делимое / Делитель КАК Число(15, 0)). Обязательно защититесь от деления на ноль конструкцией ВЫБОР КОГДА Делитель = 0 ТОГДА 0 ИНАЧЕ ... КОНЕЦ.
Что делать с NULL при преобразовании к целому?
Любая функция вернёт NULL, если на входе NULL. Оберните поле в ЕСТЬNULL(Поле, 0) до преобразования, чтобы результат был предсказуемым и корректно участвовал в итогах и группировках.
Что важно запомнить
Основной способ получить целое число в запросе 1С — функция Целое(), она усекает дробную часть без округления. Для математического округления и фиксации типа используйте ВЫРАЗИТЬ с нулевой точностью, для дат — РАЗНОСТЬДАТ. Всегда проверяйте отрицательные значения, NULL и запас разрядности.