Работа с таблицами значений в 1С:Предприятие — одна из самых частых задач для разработчиков и аналитиков. Но перед обработкой данных критически важно убедиться, что таблица не пустая. Пропуск этой проверки может привести к ошибкам выполнения, некорректным отчётам или даже падению системы при работе с большими объёмами данных. В этой статье мы разберём 5 надёжных способов проверки таблиц значений на пустоту, их плюсы и минусы, а также нюансы применения в разных версиях платформы.

Особенность таблиц значений в 1С заключается в том, что они могут быть пустыми по двум причинам: либо в них вообще нет строк (Количество() = 0), либо строки есть, но все ячейки содержат Неопределённое или пустые значения. Стандартные методы вроде ПустаяСтрока() здесь не работают — требуются специальные подходы. Далее вы найдёте готовые решения для типовых и нестандартных сценариев, включая обработку больших таблиц (100 000+ строк) без потери производительности.

1. Базовый метод: проверка количества строк

Самый простой и очевидный способ — использовать свойство Количество(). Этот метод подходит для 90% случаев, когда нужно быстро определить, есть ли в таблице хотя бы одна строка. Синтаксис минималистичен:

Если ТаблицаЗначений.Количество() = 0 Тогда

// Таблица пустая

КонецЕсли;

Преимущества метода:

  • Мгновенное выполнение — даже для таблиц с миллионом строк, так как платформа не сканирует данные, а просто возвращает служебное значение.
  • 🔧 Универсальность — работает во всех версиях 1С, включая устаревшие (7.7) и актуальные (8.3.20+).
  • 📊 Подходит для предварительной валидации перед циклами Для каждого или выгрузкой данных.

Однако у этого подхода есть критическая уязвимость: он не учитывает строки, где все колонки содержат Неопределённое или пустые значения. Например, если в таблице 10 строк, но все ячейки пустые, метод вернёт Количество() = 10, хотя фактически данных нет. Для таких случаев нужны дополнительные проверки.

⚠️ Внимание: В версиях 1С ниже 8.3.10 метод Количество() может возвращать некорректные значения для динамически изменяемых таблиц (например, при работе с временными таблицами в транзакциях). Перед использованием проверьте актуальность данных через ТаблицаЗначений.ПолучитьДанные().
📊 Какой метод проверки таблиц вы используете чаще?
Количество()
ПустаяСтрока()
Перебор строк
Запрос
Свой метод

2. Проверка на "неопределённые" и пустые значения

Если вам нужно убедиться, что в таблице есть хотя бы одна ячейка с осмысленными данными, стандартного Количество() недостаточно. В этом случае используйте комбинацию из проверки количества строк и анализа содержимого:

Функция ТаблицаПустая(ТаблицаЗначений)

Если ТаблицаЗначений.Количество() = 0 Тогда

Возврат Истина;

КонецЕсли;

Для Каждого Строка Из ТаблицаЗначений Цикл

Для Каждого Колонка Из ТаблицаЗначений.Колонки Цикл

Если НЕ ЗначениеЗаполнено(Строка[Колонка.Имя]) Тогда

Продолжить;

Иначе

Возврат Ложь; // Найдена хотя бы одна заполненная ячейка

КонецЕсли;

КонецЦикла;

КонецЦикла;

Возврат Истина; // Все ячейки пустые или неопределённые

КонецФункции;

Здесь используется вложенный цикл для перебора всех ячеек. Функция ЗначениеЗаполнено() возвращает Ложь для:

  • 🔘 Неопределённое
  • 🔘 Пустых строк ("")
  • 🔘 NULL (в внешних источниках данных)

Минус этого метода — низкая производительность для больших таблиц (от 10 000 строк). Если вам нужно проверять такие объёмы, используйте оптимизированные подходы из следующих разделов.

💡

Для ускорения проверки добавьте в функцию параметр ИмяКолонки и анализируйте только критические колонки, например: Если ЗначениеЗаполнено(Строка["Сумма"]) Тогда...

3. Оптимизированная проверка для больших таблиц

При работе с таблицами объёмом от 50 000 строк стандартный перебор становится неэффективным. В этом случае используйте запросы 1С или специализированные методы платформы. Например, так можно проверить наличие ненулевых значений в колонке "Сумма":

Запрос = Новый Запрос;

Запрос.Текст =

"ВЫБРАТЬ РАЗЛИЧНЫЕ ПЕРВЫЕ 1

| ТаблицаЗначений.Сумма КАК Сумма

|ИЗ

| &ТаблицаЗначений КАК ТаблицаЗначений

|ГДЕ

| НЕ ТаблицаЗначений.Сумма ЕСТЬ NULL

| И НЕ ТаблицаЗначений.Сумма = 0";

Запрос.УстановитьПараметр("ТаблицаЗначений", ТаблицаЗначений);

Результат = Запрос.Выполнить();

Если Результат.Пустой() Тогда

// Все суммы нулевые или неопределённые

Иначе

// Есть ненулевые значения

КонецЕсли;

Преимущества этого подхода:

  • Высокая скорость — запрос оптимизирован на уровне СУБД.
  • 🎯 Гибкость — можно добавлять условия для нескольких колонок.
  • 📈 Масштабируемость — работает даже для таблиц с миллионами строк.

Обратите внимание, что для временных таблиц (созданных через Новый ТаблицаЗначений) запрос будет работать медленнее, чем для таблиц, загруженных из базы данных. В таких случаях лучше использовать метод НайтиСтроку() с предикатом.

Метод Скорость (100к строк) Подходит для временных таблиц Учитывает неопределённые значения
Количество() 0.01 сек Да Нет
Перебор строк 1.2 сек Да Да
Запрос с ПЕРВЫЕ 1 0.05 сек Нет* Да
НайтиСтроку() 0.03 сек Да Да

* Для временных таблиц запрос будет выполняться в памяти, что замедляет работу.

4. Использование метода НайтиСтроку()

Метод НайтиСтроку() позволяет искать строки по условию без полного перебора. Это идеальный баланс между скоростью и функциональностью. Пример проверки на наличие строк, где колонка "Дата" не пустая:

НайденнаяСтрока = ТаблицаЗначений.НайтиСтроку(

Новый Структура("Дата", Неопределённое),

Новый Структура("Дата", Тип("Дата"))

);

Если НайденнаяСтрока = Неопределённое Тогда

// Все строки пустые или даты неопределённые

Иначе

// Есть хотя бы одна строка с заполненной датой

КонецЕсли;

Ключевые особенности метода:

  • 🔍 Поиск по шаблону — можно задавать условия для нескольких колонок.
  • 🚀 Быстрее перебора — останавливается при первом совпадении.
  • 🛠️ Гибкие условия — поддерживает сравнение по типам (Тип("Дата")).

Для проверки на любые непустые значения (независимо от колонки) используйте универсальный предикат:

Функция ЕстьЗначения(ТаблицаЗначений)

Для Каждого Колонка Из ТаблицаЗначений.Колонки Цикл

НайденнаяСтрока = ТаблицаЗначений.НайтиСтроку(

Новый Структура(Колонка.Имя, Неопределённое),

Новый Структура(Колонка.Имя, НЕ Тип("Неопределённое"))

);

Если НайденнаяСтрока <> Неопределённое Тогда

Возврат Истина;

КонецЕсли;

КонецЦикла;

Возврат Ложь;

КонецФункции;

⚠️ Внимание: В версиях 1С 8.3.18+ метод НайтиСтроку() поддерживает лямбда-выражения, что упрощает синтаксис. Пример: ТаблицаЗначений.Найти(Функция(Строка) Возврат Строка.Сумма > 0; КонецФункции).

5. Проверка через запрос к временной таблице

Если вам нужно проверить таблицу значений, которая является результатом предыдущего запроса, оптимально использовать механизм временных таблиц. Это позволяет избежать лишних копирований данных в память:

Запрос = Новый Запрос;

Запрос.Текст =

"ВЫБРАТЬ

| РАЗРЕШЕННЫЕ ПЕРВЫЕ 1

| 1 КАК ЕстьДанные

|ИЗ

| &ТаблицаЗначений КАК ТЗ

|ГДЕ

| НЕ ТЗ.Сумма ЕСТЬ NULL

| И НЕ ТЗ.Сумма = 0";

Запрос.УстановитьПараметр("ТаблицаЗначений", ТаблицаЗначений);

Результат = Запрос.Выполнить();

ЕстьДанные = НЕ Результат.Пустой();

Этот подход особенно полезен, когда:

  • 📋 Таблица значений получена из другого запроса (например, через Выгрузить()).
  • 🔄 Нужно проверить несколько условий одновременно (например, Сумма > 0 И Дата >= &НачалоПериода).
  • 📈 Данные планируется дальше обрабатывать через СУБД (например, агрегировать).

Для временных таблиц, созданных в памяти (через Новый ТаблицаЗначений), этот метод будет работать медленнее, чем НайтиСтроку(), но зато позволит использовать весь синтаксис языка запросов, включая ВЫБРАТЬ РАЗРЕШЕННЫЕ или ГРУППИРОВКА.

Как ускорить работу с временными таблицами?

Для ускорения добавьте индексы к колонкам, по которым выполняется поиск:

ТаблицаЗначений.Индексы.Добавить("ИндексПоСумме", Новый ИндексТаблицыЗначений("Сумма"));

Это уменьшит время выполнения НайтиСтроку() и запросов в 2-5 раз.

6. Специализированные случаи: пустые строки и колонки

Иногда требуется не просто проверить таблицу на пустоту, а выявить конкретные проблемы:

  • 📛 Пустые строки — строки без данных, но физически существующие.
  • 📊 Пустые колонки — колонки, где все значения Неопределённое.
  • 🔄 Дублирующиеся пустые строки — часто возникают при выгрузке данных из внешних источников.

Для таких задач используйте комбинацию методов. Например, чтобы удалить все пустые строки:

Процедура УдалитьПустыеСтроки(ТаблицаЗначений)

ИндексыУдаляемыхСтрок = Новый Массив;

Для Инд = ТаблицаЗначений.Количество() - 1 По 0 Цикл

Строка = ТаблицаЗначений[Инд];

ПустаяСтрока = Истина;

Для Каждого Колонка Из ТаблицаЗначений.Колонки Цикл

Если ЗначениеЗаполнено(Строка[Колонка.Имя]) Тогда

ПустаяСтрока = Ложь;

Прервать;

КонецЕсли;

КонецЦикла;

Если ПустаяСтрока Тогда

ИндексыУдаляемыхСтрок.Добавить(Инд);

КонецЕсли;

КонецЦикла;

Для Инд = ИндексыУдаляемыхСтрок.Количество() - 1 По 0 Цикл

ТаблицаЗначений.Удалить(ИндексыУдаляемыхСтрок[Инд]);

КонецЦикла;

КонецПроцедуры;

Для проверки пустых колонок используйте аналогичную логику, но перебирайте колонки, а не строки. Это актуально, например, при подготовке данных для отчётов, где пустые колонки могут искажать результаты.

Убедитесь, что таблица инициализирована|Проверить количество строк (Количество())|При необходимости анализировать содержимое ячеек|Для больших таблиц использовать запросы или НайтиСтроку()|Удалить пустые строки/колонки при необходимости-->

Типичные ошибки и как их избежать

При проверке таблиц значений на пустоту разработчики часто допускают ошибки, которые приводят к некорректной работе кода. Вот самые распространённые из них:

  1. Игнорирование неопределённых значений. Код вроде Если ТаблицаЗначений[0][0] = "" Тогда не сработает, если ячейка содержит Неопределённое. Всегда используйте ЗначениеЗаполнено().
  2. Проверка только первой строки. Если таблица содержит 100 строк, но только 99-я не пустая, проверка первой строки даст ложный результат. Используйте циклы или НайтиСтроку().
  3. Забывают про колонки. Даже если в таблице 1 строка, но все её колонки пустые, фактически данных нет. Проверяйте содержимое ячеек, а не только наличие строк.
  4. Не учитывают производительность. Перебор 100 000 строк в цикле может занять несколько секунд. Для больших таблиц используйте запросы или НайтиСтроку().

Ещё одна распространённая проблема — работа с динамически изменяемыми таблицами. Например, если таблица заполняется в фоновом задании, а проверка выполняется в основном потоке, данные могут быть неактуальными. В таких случаях используйте блокировки:

Блокировка = Новый БлокировкаДанных;

Попытка

Блокировка.Заблокировать(ТаблицаЗначений);

// Проверка и обработка данных

Исключение

Сообщить("Не удалось заблокировать таблицу: " + ОписаниеОшибки());

КонецПопытки;

⚠️ Внимание: В управляемых формах 1С таблицы значений могут автоматически очищаться при закрытии формы. Если вам нужно сохранить данные, используйте Копировать() для создания независимой копии таблицы.
💡

Для надёжной проверки таблицы на пустоту всегда комбинируйте метод Количество() с анализом содержимого ячеек. Это защитит ваш код от ошибок, связанных с неопределёнными значениями или пустыми строками.

FAQ: Частые вопросы по проверке таблиц значений

Как проверить таблицу значений на пустоту в 1С 7.7?

В версии 7.7 нет метода Количество(), но можно использовать:

Если ТаблицаЗначений.ВыбратьСтроки().Следующий() = 0 Тогда

// Таблица пустая

КонецЕсли;

Для проверки содержимого ячеек используйте ПустоеЗначение() вместо ЗначениеЗаполнено().

Почему Количество() возвращает 1, хотя таблица визуально пустая?

Это происходит, если в таблице есть "призрачная" строка — строка без данных, но физически существующая. Чтобы удалить такие строки, используйте:

Пока ТаблицаЗначений.Количество() > 0 И НЕ ЗначениеЗаполнено(ТаблицаЗначений[0][0]) Цикл

ТаблицаЗначений.Удалить(0);

КонецЦикла;

Как ускорить проверку таблицы с 1 000 000 строк?

Для таких объёмов:

  1. Используйте НайтиСтроку() с предикатом.
  2. Если нужно проверить несколько колонок, создайте составной индекс:
  3. ТаблицаЗначений.Индексы.Добавить("ИндексПоДатамИСуммам",
    

    Новый ИндексТаблицыЗначений("Дата, Сумма"));

  4. Разбейте таблицу на части (по 100 000 строк) и проверяйте каждую часть параллельно.
Можно ли проверить таблицу значений на пустоту через запрос без временных таблиц?

Да, если таблица получена из базы данных. Пример:

Запрос = Новый Запрос;

Запрос.Текст = "ВЫБРАТЬ РАЗРЕШЕННЫЕ ПЕРВЫЕ 1 1 КАК ЕстьДанные ИЗ &Таблица";

Запрос.УстановитьПараметр("Таблица", ТаблицаЗначений);

Результат = Запрос.Выполнить();

ЕстьДанные = НЕ Результат.Пустой();

Для таблиц, созданных в памяти, этот метод не подходит — используйте НайтиСтроку().

Как проверить, что все строки в таблице одинаковые (например, все суммы равны 0)?

Используйте запрос с группировкой:

Запрос = Новый Запрос;

Запрос.Текст =

"ВЫБРАТЬ

| ВЫБОР

| КОГДА МАКСИМУМ(ТЗ.Сумма) = МИНИМУМ(ТЗ.Сумма)

| И МАКСИМУМ(ТЗ.Сумма) = 0

| ТОГДА Истина

| ИНАЧЕ Ложь

| КОНЕЦ КАК ВсеСуммыНулевые

|ИЗ

| &ТаблицаЗначений КАК ТЗ";

Запрос.УстановитьПараметр("ТаблицаЗначений", ТаблицаЗначений);

Результат = Запрос.Выполнить().Выгрузить();

ВсеСуммыНулевые = Результат[0].ВсеСуммыНулевые;