Как искать строки со спецсимволами в запросе 1С с помощью оператора ПОДОБНО?

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

При написании запросов к базе данных 1С разработчики часто используют оператор проверки на соответствие шаблону ПОДОБНО. Однако при попытке найти строку, которая сама по себе содержит квадратные скобки (например, артикул, код или номер вида [000654]), процент % или знак подчеркивания _, стандартное условие начинает работать некорректно. Это происходит потому, что данные символы являются управляющими конструкциями шаблона. Разберем, как правильно экранировать служебные знаки в языке запросов платформы 1С:Предприятие.

Служебные символы оператора ПОДОБНО

Рассмотрим, какие именно символы зарезервированы платформой внутри строки шаблона:

  1. Знак процента % — обозначает последовательность из любого количества произвольных символов (включая нулевую длину).
  2. Знак подчеркивания _ — обозначает строго один произвольный символ.
  3. Квадратные скобки [...] — обозначают любой одиночный символ из перечисленных внутри скобок (например, [0-9] или [абвг]).
  4. Символ отрицания в скобках [^...] — обозначает любой одиночный символ, кроме тех, что перечислены внутри.

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

Использование конструкции СПЕЦСИМВОЛ

Проанализируем стандартный и самый надежный способ экранирования — указание директивы СПЕЦСИМВОЛ. Данная конструкция объявляется в конце выражения сравнения и задает один конкретный символ, который будет сообщать платформе: следующий за ним символ шаблона нужно воспринимать буквально.

Посмотрим на пример запроса, где в наименовании ищется подстрока [000654]:


ВЫБРАТЬ
    Номенклатура.Ссылка КАК Ссылка,
    Номенклатура.Наименование КАК Наименование
ИЗ
    Справочник.Номенклатура КАК Номенклатура
ГДЕ
    Номенклатура.Наименование ПОДОБНО "%\[000654\]%" СПЕЦСИМВОЛ "\"

В приведенном запросе мы назначили обратный слэш \ в качестве символа экранирования. Перед открывающей квадратной скобкой \[ и перед закрывающей \] мы указали этот спецсимвол, благодаря чему платформа воспринимает их как обычные печатные знаки текста.

Важное ограничение: литерал после ключевого слова СПЕЦСИМВОЛ обязан быть строкой длиной ровно в один символ (например, "\", "~", "#"). Передавать этот символ через параметр запроса нельзя — синтаксис языка запросов 1С требует явного указания литерала.

Альтернативный способ экранирования скобок без ключевого слова СПЕЦСИМВОЛ

Рассмотрим еще одну синтаксическую особенность шаблонов. Открывающую квадратную скобку можно экранировать, поместив её внутрь самого диапазона квадратных скобок — [[]. В этом случае закрывающая скобка вне диапазона автоматически трактуется как обычный символ.

Посмотрим, как выглядит такой запрос:


ВЫБРАТЬ
    Номенклатура.Ссылка КАК Ссылка,
    Номенклатура.Наименование КАК Наименование
ИЗ
    Справочник.Номенклатура КАК Номенклатура
ГДЕ
    Номенклатура.Наименование ПОДОБНО "%[[]000654]%"

Этот способ позволяет обойтись без конструкции СПЕЦСИМВОЛ, если требуется экранировать только квадратные скобки.

Динамическое формирование шаблона в коде 1С

Если строка поиска вводится пользователем динамически и передается в запрос через параметр, все спецсимволы в ней необходимо предварительно экранировать во встроенном языке.

Разберем по шагам правильный алгоритм экранирования. Критически важно соблюдать очередность замен: первым делом экранируется сам назначенный символ экранирования, и только затем все остальные служебные знаки шаблона.


// Допустим, пользователь ввел строку: [000654]_тест%
СтрокаПоиска = ВходнойТекст;

// 1. В первую очередь экранируем сам escape-символ (обратный слэш)
СтрокаПоиска = СтрЗаменить(СтрокаПоиска, "\", "\\");

// 2. Экранируем процент, подчеркивание и открывающую скобку
СтрокаПоиска = СтрЗаменить(СтрокаПоиска, "%", "\%");
СтрокаПоиска = СтрЗаменить(СтрокаПоиска, "_", "\_");
СтрокаПоиска = СтрЗаменить(СтрокаПоиска, "[", "\[");
СтрокаПоиска = СтрЗаменить(СтрокаПоиска, "]", "\]");

// 3. Формируем итоговый шаблон для поиска по подстроке
ШаблонЗапроса = "%" + СтрокаПоиска + "%";

Запрос = Новый Запрос;
Запрос.Текст = 
    "ВЫБРАТЬ
    |	Номенклатура.Ссылка КАК Ссылка,
    |	Номенклатура.Наименование КАК Наименование
    |ИЗ
    |	Справочник.Номенклатура КАК Номенклатура
    |ГДЕ
    |	Номенклатура.Наименование ПОДОБНО &Шаблон СПЕЦСИМВОЛ ""\""";

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

Если нарушить последовательность и заменить слэш в последнюю очередь, все ранее расставленные знаки \ продублируются в \\, что приведет к искажению шаблона поиска.

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

Проанализируем влияние оператора ПОДОБНО на быстродействие базы данных:

  1. Проблема сканирования таблиц: Шаблон с ведущим процентом (например, "%[000654]%") делает невозможным использование индексов СУБД. Происходит полное сканирование таблицы (Full Scan), что на больших объемах данных приводит к длительным блокировкам и падению производительности.
  2. Полнотекстовый поиск: Если пользователям необходим регулярный поиск по произвольным подстрокам, рекомендуется использовать объект ПолнотекстовыйПоиск, работающий по специализированному индексу.
  3. Выделение отдельного реквизита: Если в скобках хранится значимый код, артикул или идентификатор, оптимальным решением является выделение его в отдельный индексированный реквизит объекта. Сравнение через = или поиск по префиксу ("000654%" без начального процента) позволяет СУБД эффективно использовать индекс.
← На главную