В работе с данными часто возникает необходимость валидировать вводимую или получаемую информацию. Одной из распространённых задач является проверка строки на содержание только определённого набора допустимых символов. Если в строке обнаруживаются посторонние символы, об этом необходимо сообщить. Давайте разберем несколько подходов к решению этой задачи в системе 1С:Предприятие, используя как встроенные функции платформы, так и более продвинутые методы. Мы рассмотрим различные сценарии и выберем наиболее подходящие решения.
Этот подход является одним из наиболее прямых и понятных. Мы будем последовательно проходить по каждому символу в исходной строке и проверять, содержится ли он в заранее определенном наборе допустимых символов. Если на каком-либо этапе будет найден символ, отсутствующий в этом наборе, мы можем сразу сделать вывод о наличии недопустимых символов и прекратить проверку.
Рассмотрим подробнее, как это реализовать. Нам потребуется функция, которая принимает строку для проверки. Внутри этой функции мы организуем цикл от первого до последнего символа строки. Для каждого символа мы используем функцию Найти(), чтобы определить, есть ли он в строке допустимых символов.
Предположим, что допустимыми символами являются вертикальная черта (|) и все цифры от 0 до 9. Мы можем сформировать строку-список допустимых символов "|0123456789".
// Исходная строка для проверки
СтрокаДляПроверки = "|67894376|";
// Строка, содержащая все допустимые символы
ДопустимыеСимволы = "|0123456789";
Функция ПроверитьСтрокуНаНедопустимыеСимволы(ИсходнаяСтрока)
Для Сч = 1 По СтрДлина(ИсходнаяСтрока) Цикл
ТекущийСимвол = Сред(ИсходнаяСтрока, Сч, 1);
Если Найти(ДопустимыеСимволы, ТекущийСимвол) = 0 Тогда
// Символ не найден в списке допустимых, значит он недопустимый
Возврат Истина; // Возвращаем Истина, если найден недопустимый символ
КонецЕсли;
КонецЦикла;
// Если цикл завершился, значит все символы допустимы
Возврат Ложь; // Возвращаем Ложь, если все символы допустимы
КонецФункции
Если ПроверитьСтрокуНаНедопустимыеСимволы(СтрокаДляПроверки) Тогда
Сообщить("Строка содержит недопустимые символы!");
Иначе
Сообщить("Строка содержит только допустимые символы.");
КонецЕсли;
// Пример использования с недопустимыми символами
СтрокаСОшибкакой = "|123АВС|";
Если ПроверитьСтрокуНаНедопустимыеСимволы(СтрокаСОшибкакой) Тогда
Сообщить("Строка с ошибкой содержит недопустимые символы!");
Иначе
Сообщить("Строка с ошибкой содержит только допустимые символы.");
КонецЕсли;
Преимущества этого метода заключаются в его простоте и очевидности. Он легко читается и понимается, а также достаточно надежен. Как только недопустимый символ найден, функция немедленно завершает работу, что экономит ресурсы на дальнейший перебор.
Однако есть и недостатки. Для очень длинных строк или для случаев, когда набор допустимых символов очень велик, многократные вызовы функции Найти() могут быть неоптимальными с точки зрения производительности. Каждый вызов Найти() для каждого символа может потребовать дополнительного времени.
Этот метод предлагает несколько иной подход: вместо поиска допустимых символов, мы попытаемся разделить исходную строку, используя в качестве разделителей все допустимые символы. Если после такого разделения в полученном массиве останутся какие-либо непустые элементы, это будет означать, что исходная строка содержала символы, которые не были использованы в качестве разделителей, то есть недопустимые символы.
Разберем по шагам, как это работает. Функция СтрРазделить() принимает исходную строку, строку-разделитель и необязательный параметр, указывающий, включать ли пустые строки в результат. Для нашей задачи критически важно использовать параметр "не включать пустые строки" (Ложь), чтобы избежать ложных срабатываний.
В качестве строки-разделителя мы указываем все допустимые символы: "|0123456789".
// Исходная строка для проверки
СтрокаДляПроверки = "|67894376|";
// Строка, содержащая все допустимые символы, которые будут использоваться как разделители
Разделители = "|0123456789";
Функция ПроверитьСтрокуНаНедопустимыеСимволыСтрРазделить(ИсходнаяСтрока)
// Разделяем строку, используя допустимые символы как разделители.
// Параметр Ложь указывает не включать пустые строки в результат.
МассивОставшихсяЧастей = СтрРазделить(ИсходнаяСтрока, Разделители, Ложь);
// Если количество элементов в массиве больше нуля,
// значит, остались части, которые не удалось разделить допустимыми символами.
// Эти части и содержат недопустимые символы.
Если МассивОставшихсяЧастей.Количество() > 0 Тогда
Возврат Истина; // Найдены недопустимые символы
Иначе
Возврат Ложь; // Все символы были допустимыми разделителями
КонецЕсли;
КонецФункции
Если ПроверитьСтрокуНаНедопустимыеСимволыСтрРазделить(СтрокаДляПроверки) Тогда
Сообщить("Строка содержит недопустимые символы!");
Иначе
Сообщить("Строка содержит только допустимые символы.");
КонецЕсли;
// Пример использования с недопустимыми символами
СтрокаСОшибкакой = "|123АВС|";
Если ПроверитьСтрокуНаНедопустимыеСимволыСтрРазделить(СтрокаСОшибкакой) Тогда
Сообщить("Строка с ошибкой содержит недопустимые символы!");
Иначе
Сообщить("Строка с ошибкой содержит только допустимые символы.");
КонецЕсли;
Преимущество этого метода в его элегантности и потенциально более высокой производительности для некоторых случаев, так как он использует одну мощную встроенную функцию платформы. Он хорошо подходит, когда нам нужно быстро определить наличие любых символов, отличных от заданного набора.
Недостатком может быть менее очевидная логика для начинающих, а также тот факт, что сама функция СтрРазделить() может быть относительно ресурсоемкой при работе с очень длинными строками и большим количеством разделителей, так как она создает промежуточный массив.
Этот метод интуитивно понятен: мы берем исходную строку и последовательно удаляем из нее все допустимые символы. Если после этой операции строка остается непустой, значит, в ней были символы, которые не удалось удалить, то есть недопустимые символы.
Для реализации этого подхода мы можем использовать функцию СтрЗаменить() в цикле. Мы будем проходить по каждому допустимому символу и заменять его на пустую строку в копии исходной строки.
// Исходная строка для проверки
СтрокаДляПроверки = "|67894376|";
// Строка, содержащая все допустимые символы, которые будут удаляться
ДопустимыеСимволы = "|0123456789";
Функция ПроверитьСтрокуНаНедопустимыеСимволыСтрЗаменить(ИсходнаяСтрока)
// Создаем копию строки, чтобы не изменять исходную
СтрокаБезДопустимых = ИсходнаяСтрока;
// Перебираем каждый допустимый символ
Для Сч = 1 По СтрДлина(ДопустимыеСимволы) Цикл
ТекущийДопустимыйСимвол = Сред(ДопустимыеСимволы, Сч, 1);
// Заменяем все вхождения текущего допустимого символа на пустую строку
СтрокаБезДопустимых = СтрЗаменить(СтрокаБезДопустимых, ТекущийДопустимыйСимвол, "");
КонецЦикла;
// Если после удаления всех допустимых символов строка не пуста,
// значит, в ней остались недопустимые символы.
Если СтрДлина(СтрокаБезДопустимых) > 0 Тогда
Возврат Истина; // Найдены недопустимые символы
Иначе
Возврат Ложь; // Все символы были допустимыми
КонецЕсли;
КонецФункции
Если ПроверитьСтрокуНаНедопустимыеСимволыСтрЗаменить(СтрокаДляПроверки) Тогда
Сообщить("Строка содержит недопустимые символы!");
Иначе
Сообщить("Строка содержит только допустимые символы.");
КонецЕсли;
// Пример использования с недопустимыми символами
СтрокаСОшибкакой = "|123АВС|";
Если ПроверитьСтрокуНаНедопустимыеСимволыСтрЗаменить(СтрокаСОшибкакой) Тогда
Сообщить("Строка с ошибкой содержит недопустимые символы!");
Иначе
Сообщить("Строка с ошибкой содержит только допустимые символы.");
КонецЕсли;
Преимущество этого метода также в его простоте и относительно легкости понимания. Он хорошо работает для строк умеренной длины и небольшого количества допустимых символов.
Основной недостаток заключается в потенциальных проблемах с производительностью. Каждая операция СтрЗаменить() создает новую строку. Если допустимых символов много, а исходная строка очень длинная, это может привести к значительным накладным расходам на создание и удаление временных строковых объектов.
В типовых конфигурациях 1С, основанных на Библиотеке Стандартных Подсистем (БСП), часто присутствуют вспомогательные функции для работы со строками. Одной из таких функций, упомянутых в обсуждении, является ОбщегоНазначенияКлиентСервер.ТолькоЦифры() или аналогичные.
Важно понимать: функции БСП, такие как ТолькоЦифры(), обычно предназначены для извлечения только цифр из строки или проверки, что строка состоит только из цифр. Они не будут учитывать другие допустимые символы, такие как |, которые требуются в нашей задаче.
Если бы задача состояла только в проверке на цифры, мы могли бы использовать:
ИсходнаяСтрока = "123456";
Если ОбщегоНазначенияКлиентСервер.ТолькоЦифры(ИсходнаяСтрока) = ИсходнаяСтрока Тогда
Сообщить("Строка содержит только цифры.");
Иначе
Сообщить("Строка содержит недопустимые символы (не цифры).");
КонецЕсли;
Для нашей конкретной задачи, которая включает как цифры, так и символ |, универсальной функции в БСП, проверяющей произвольный набор допустимых символов, может не быть. В этом случае, вероятно, придется комбинировать или использовать один из вышеописанных кастомных методов. Например, можно сначала очистить строку от цифр с помощью БСП-функции, а затем проверить оставшееся на наличие символов |. Для расширения возможностей стандартных строковых функций подойдёт библиотека дополнительных методов обработки строк в 1С.
Для более сложных и гибких задач валидации строк, а также для потенциального повышения производительности, существуют более продвинутые подходы.
VBScript.RegExp. Регулярные выражения позволяют очень точно описывать допустимый шаблон строки.Для нашей задачи (строка начинается/заканчивается на |, внутри только цифры, или только цифры) регулярное выражение могло бы выглядеть так: ^\|?\d+\|?$.
Разберем это выражение:
^ – якорь начала строки.\|? – необязательная вертикальная черта (символ | экранирован как \|) в начале.\d+ – одна или более цифр (\d обозначает любую цифру, + означает одно или более вхождений).\|? – необязательная вертикальная черта в конце.$ – якорь конца строки.Использование регулярных выражений значительно сокращает объем кода для сложных проверок и может быть очень производительным, но требует подключения внешних объектов и знания синтаксиса RegEx.
КодСимвола() и сравнении его с диапазонами допустимых кодов. Для цифр, например, коды символов находятся в диапазоне от 48 (для '0') до 57 (для '9'). Для символа | код равен 124.Такой подход может быть более производительным, чем многократные вызовы Найти() по длинной строке допустимых символов, так как сравнение чисел обычно быстрее, чем поиск подстроки.
Функция ПроверитьСтрокуНаНедопустимыеСимволыПоКоду(ИсходнаяСтрока)
Для Сч = 1 По СтрДлина(ИсходнаяСтрока) Цикл
ТекущийКодСимвола = КодСимвола(Сред(ИсходнаяСтрока, Сч, 1));
// Проверяем, является ли символ цифрой (коды 48-57)
// или вертикальной чертой (код 124)
Если НЕ ( (ТекущийКодСимвола >= 48 И ТекущийКодСимвола <= 57)
ИЛИ (ТекущийКодСимвола = 124) ) Тогда
Возврат Истина; // Найден недопустимый символ
КонецЕсли;
КонецЦикла;
Возврат Ложь; // Все символы допустимы
КонецФункции
Этот метод является очень эффективным и явным, особенно когда вы работаете с четко определенными наборами символов или символами в определенных диапазонах.
Заключение: Как мы видим, в 1С существует несколько эффективных способов для проверки строк на наличие недопустимых символов. Выбор конкретного метода зависит от ваших требований к производительности, читаемости кода и сложности проверяемого шаблона. Для простых случаев вполне подойдут посимвольный перебор или метод СтрРазделить()/СтрЗаменить(). Для более сложных и ресурсоемких задач можно рассмотреть проверку кодов символов или интеграцию с регулярными выражениями через внешние компоненты. Главное — всегда четко определять набор допустимых символов и выбирать метод, который наилучшим образом соответствует поставленной задаче. Для внедрения проверки строк по сложным шаблонам можно использовать подсистему для работы с регулярными выражениями в 1С.