Как работают индексы реквизитов в регистрах 1С и можно ли создать эффективный отдельный индекс?

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

В процессе разработки и оптимизации высоконагруженных систем на платформе 1С:Предприятие 8 часто возникает вопрос производительности запросов к регистрам. Одной из ключевых тем здесь является индексация. Многие разработчики опасаются, что при индексации реквизита создается слишком «тяжелый» или неэффективный индекс, который не поможет при поиске только по этому полю. Рассмотрим подробно, как именно платформа управляет индексами, и выясним, нужно ли прибегать к средствам СУБД для ручной настройки.

Разберем механизм формирования индексов в регистрах

Проанализируем стандартное поведение платформы при работе с регистрами сведений и накопления. В 1С состав индексов жестко определен логикой ядра. Когда мы устанавливаем свойство Индексировать у реквизита регистра, платформа не просто создает индекс по одному этому полю. Она формирует составной индекс, структура которого выглядит следующим образом:

[Индексируемый Реквизит] + [Измерение 1] + [Измерение 2] + ...

Рассмотрим, почему это происходит. Добавление измерений в конец индекса необходимо платформе для обеспечения уникальности записей (для регистров сведений) или для оптимизации доступа к данным в контексте уникальных комбинаций ключей. На первый взгляд может показаться, что такой «раздутый» индекс будет работать медленно, если нам нужно найти данные только по Реквизиту 1. Однако здесь вступает в силу фундаментальное правило работы индексов в СУБД.

Проанализируем «правило левой части»

Для понимания эффективности поиска важно вспомнить «правило префикса» или «правило левой части». Любой составной индекс по полям (A + B + C) будет эффективно использоваться оптимизатором запросов в следующих случаях:

  1. Если в условии запроса (ГДЕ) указано только поле А.
  2. Если указаны поля А и В.
  3. Если указаны все три поля А, В и С.

Если же в условии указано только поле В или только поле С, данный индекс работать не будет, и СУБД перейдет к сканированию всей таблицы (Table Scan), что критично для производительности. Поскольку 1С ставит индексируемый реквизит на первое место в создаваемом индексе, поиск по этому реквизиту будет работать максимально быстро. Тот факт, что в индексе присутствуют измерения, никак не мешает быстрому поиску по первому полю, а лишь добавляет в индекс дополнительную информацию.

Выясним причину сомнений: «Индексировать с дополнительным упорядочиванием»

Иногда разработчики ищут в регистрах опцию Индексировать с дополнительным упорядочиванием, которая доступна для справочников. Рассмотрим ситуацию: в справочниках эта настройка создает дополнительные индексы для ускорения сортировки в списках. Однако для регистров такая опция в метаданных отсутствует.

Важно понимать, что для регистра свойство Индексировать фактически уже работает аналогично этой опции. Платформа создает отдельную индексную группу, где первым элементом идет выбранный реквизит. Таким образом, мы получаем отдельную структуру поиска, которая не смешивается с основным кластерным индексом таблицы (который обычно строится по Периоду и Измерениям).

Риски и последствия ручного создания индексов на уровне SQL

Рассмотрим ситуацию, когда разработчик решает обойти ограничения платформы и создать «идеальный» индекс напрямую через MS SQL Management Studio или консоль PostgreSQL. На первый взгляд, это кажется логичным — создать легкий индекс только по одному полю или даже «покрывающий индекс» с использованием конструкции INCLUDE. Однако проанализируем риски такого подхода:

  1. Реструктуризация данных: Это самая главная проблема. При любом изменении состава полей регистра или даже изменении длины строки реквизита платформа 1С выполняет реструктуризацию. Она создает временную таблицу _temp, переносит туда данные, удаляет старую таблицу и переименовывает новую. В этот момент все ваши индексы, созданные вручную на уровне СУБД, будут безвозвратно удалены.
  2. Лицензионная чистота: Прямое изменение структуры таблиц базы данных (включая создание индексов) является формальным нарушением условий лицензионного соглашения 1С. В критических ситуациях это может стать проблемой при аудите системы.
  3. Обновление конфигурации: При обновлении или внесении изменений через конфигуратор вы рискуете забыть о ручных правках, что приведет к внезапному падению производительности, когда индекс «слетит».

Посмотрим на альтернативные методы оптимизации

Если штатной индексации недостаточно, разберем, какие еще инструменты есть в арсенале разработчика 1С:

1. Использование «Критериев отбора»
Для организации быстрого поиска по реквизитам документов или справочников можно использовать объект метаданных КритерииОтбора. Это позволяет платформе строить свои внутренние механизмы связи, которые могут быть эффективнее простых запросов.

2. Полнотекстовый поиск (ППС)
Если вам требуется поиск по строковым реквизитам (например, поиск по части наименования или описания), создание обычного индекса может не помочь. В этом случае лучше использовать механизм ППС. Он создает отдельные индексные файлы вне базы данных SQL, что позволяет выполнять сложные поисковые запросы, не нагружая транзакционную систему СУБД.

3. Оптимизация виртуальных таблиц
Часто проблема кроется не в поиске по физической таблице регистра, а в обращении к виртуальным таблицам (Остатки, СрезПоследних). Проанализируем запрос: если вы накладываете условие на реквизит внутри параметров виртуальной таблицы, 1С старается применить индексы. Однако наиболее эффективно условия работают именно по измерениям. Если поиск по реквизиту в виртуальной таблице медленный, стоит рассмотреть возможность перевода этого реквизита в статус измерения (если позволяет логика уникальности).

Пример анализа индекса через запрос

Рассмотрим, как убедиться, что индекс работает. Для этого в консоли запросов с включенным планом выполнения (или через SQL Profiler) мы можем увидеть использование индекса. В коде 1С мы пишем обычный запрос:


Запрос = Новый Запрос;
Запрос.Текст = 
    "ВЫБРАТЬ
    |   РегистрСведений1.Ресурс1 КАК Ресурс1
    |ИЗ
    |   РегистрСведений.РегистрСведений1 КАК РегистрСведений1
    |ГДЕ
    |   РегистрСведений1.Реквизит1 = &ЗначениеРеквизита";

Запрос.УстановитьПараметр("ЗначениеРеквизита", ИскомоеЗначение);
Результат = Запрос.Выполнить();

Если у Реквизит1 установлено свойство Индексировать, то в плане SQL-запроса мы увидим операцию Index Seek по индексу, начинающемуся с этого реквизита. Это и есть подтверждение того, что «отдельный» индекс работает корректно в рамках логики 1С.

Подведем итоги

Проанализировав поведение платформы, мы пришли к выводу, что штатный механизм индексации реквизитов в 1С вполне самодостаточен. Несмотря на то, что 1С добавляет измерения в индекс, благодаря «правилу левой части» поиск остается эффективным.

Основные рекомендации:

Таким образом, мы выяснили, что опасения по поводу неработоспособности индексов в 1С при поиске по реквизиту беспочвенны — платформа проектировалась с учетом оптимизации таких операций.

← На главную