При разработке отчетов или обработок, работающих с остатками товаров, программисты часто сталкиваются с вопросом архитектуры запроса. Как минимизировать нагрузку на базу данных, избежать блокировок и получить необходимые данные (остатки, список складов и номенклатуру) наиболее чисто с точки зрения кода? Давайте разберем наиболее эффективные подходы.
Самым надежным и профессиональным способом является использование временных таблиц. При работе с большими объемами данных важно не просто получить результат, а сделать это так, чтобы СУБД построила оптимальный план выполнения запроса. Помещение результата выборки остатков во временную таблицу позволяет системе зафиксировать «снимок» данных.
Рассмотрим структуру такого подхода:
ВременнуюТаблицу.ВременнуюТаблицу (например, используя ВЫБРАТЬ РАЗЛИЧНЫЕ) для получения уникального списка складов и товаров.ВременнуюТаблицу сразу после выполнения пакета, что освобождает нас от необходимости ручного удаления и обеспечивает чистоту кода.Почему это быстрее? Потому что СУБД работает с индексированным набором данных в памяти или временном хранилище, а не обращается повторно к тяжелым физическим таблицам итогов регистра.
При выполнении запросов важно учитывать состояние данных. Если вы выполняете несколько запросов отдельно, существует риск, что данные между ними изменятся. Использование пакетного запроса с временной таблицей решает проблему консистентности: все выборки в рамках одного пакета будут работать с одним и тем же снимком данных.
Что касается блокировок, при выполнении запроса к регистрам 1С накладывается S-блокировка (разделяемая блокировка), что гарантирует целостность считываемой информации. Использование временной таблицы позволяет единожды наложить эту блокировку на исходный набор данных, а последующие операции проводить уже над выборкой, что благоприятно сказывается на общей производительности системы.
Рассмотрим пример того, как это выглядит на практике:
ВЫБРАТЬ
Остатки.Номенклатура,
Остатки.Склад,
Остатки.КоличествоОстаток
ПОМЕСТИТЬ ВТ_Остатки
ИЗ
РегистрНакопления.ТоварыНаСкладах.Остатки(&Период, ) КАК Остатки
;
ВЫБРАТЬ РАЗЛИЧНЫЕ
ВТ_Остатки.Склад
ИЗ
ВТ_Остатки КАК ВТ_Остатки
;
ВЫБРАТЬ РАЗЛИЧНЫЕ
ВТ_Остатки.Номенклатура
ИЗ
ВТ_Остатки КАК ВТ_Остатки
Этот подход имеет ряд неоспоримых преимуществ:
Важно понимать, что если объем данных в базе небольшой (например, несколько сотен или тысяч записей), то существенной разницы в скорости между тремя отдельными запросами и пакетом с временными таблицами вы можете не заметить. В таких случаях можно выбирать тот вариант, который кажется наиболее лаконичным. Однако, для профессиональной разработки мы рекомендуем сразу использовать подход с временными таблицами — это отличная привычка, которая обезопасит ваш код от проблем при масштабировании базы данных.
Помните, что для сложных отчетов, где данные требуется передавать между разными процедурами, целесообразно использовать объект МенеджерВременныхТаблиц. Это позволит вам создать один раз ВТ_Остатки и обращаться к ней из любого места программного модуля, не выполняя избыточных вычислений.
Подводя итог, проанализировав ситуацию, мы рекомендуем всегда отдавать предпочтение пакетным запросам с временными таблицами как наиболее стабильному и современному решению для платформы 1С.