К статье
Практический материал

Разработка и Конфигурация · 12 мин

Как найти цифру в строке в 1С

Способы найти цифру в строке в 1С: перебор символов, функция СтрНайти, регулярные выражения в запросах, извлечение чисел из строки. Готовый код с пояснениями.

Задача найти цифру в строке возникает в 1С постоянно: нужно проверить, содержит ли артикул номер, извлечь количество из наименования, отфильтровать строки с цифрами или очистить текст от лишних символов. Встроенного оператора «есть ли цифра в строке» в языке 1С нет, поэтому задачу решают несколькими способами — от простого перебора символов до регулярных выражений в запросах.

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

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

Как проверить, есть ли цифра в строке, перебором символов

Самый надёжный и понятный способ — пройти по строке циклом и проверить каждый символ на вхождение в строку «0123456789». Функция СтрНайти() возвращает позицию найденного символа или 0, если символа нет. Этот подход работает везде: на клиенте, на сервере, в любой конфигурации, и не требует внешних компонент.

Функция ЕстьЦифраВСтроке(ПроверяемаяСтрока) Экспорт

Цифры = "0123456789";

ДлинаСтроки = СтрДлина(ПроверяемаяСтрока);

Для Позиция = 1 По ДлинаСтроки Цикл

Символ = Сред(ПроверяемаяСтрока, Позиция, 1);

Если СтрНайти(Цифры, Символ) > 0 Тогда

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

КонецЕсли;

КонецЦикла;

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

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

Функция возвращает Истина, как только встречает первую цифру, и не тратит время на остаток строки. На коротких строках (наименования, артикулы, номера) такой перебор отрабатывает мгновенно. Проблемы с производительностью начинаются только при обработке сотен тысяч строк в цикле — для таких случаев лучше фильтровать данные запросом.

Обратите внимание: проверка через СтрНайти("0123456789", Символ) корректно работает только для одного символа. Если передать туда строку длиннее одного знака, функция будет искать подстроку, и логика сломается.

Как найти позицию первой цифры в строке

Иногда нужен не факт наличия, а место, где цифра стоит: например, чтобы отрезать числовую часть артикула или разделить строку на текст и номер. Для этого цикл модифицируется — вместо булева значения возвращается позиция.

Функция ПозицияПервойЦифры(ПроверяемаяСтрока) Экспорт

Цифры = "0123456789";

Для Позиция = 1 По СтрДлина(ПроверяемаяСтрока) Цикл

Если СтрНайти(Цифры, Сред(ПроверяемаяСтрока, Позиция, 1)) > 0 Тогда

Возврат Позиция;

КонецЕсли;

КонецЦикла;

Возврат 0; // цифр нет

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

Возврат нуля — осознанное соглашение: в 1С нумерация символов строки начинается с единицы, поэтому 0 однозначно означает «цифра не найдена». Всегда проверяйте этот результат перед тем, как использовать позицию в Сред() или Лев(), иначе получите ошибку или пустую строку там, где ожидали данные.

Типовой сценарий использования — разделение строки вида «Товар123» на текстовую и числовую части: Лев(Строка, Позиция - 1) даст «Товар», а Сред(Строка, Позиция) — «123».

Порядок действий
  1. 1
    Определите, что нужно получить: факт наличия цифры, её позицию или само число
  2. 2
    Выберите способ: перебор символов для кода, ПОДОБНО для запроса
  3. 3
    Вставьте готовую функцию в общий модуль или обработку
  4. 4
    Проверьте функцию на строках без цифр, с цифрой в начале и в конце
  5. 5
    Убедитесь, что пустая строка и строка из пробелов не вызывают ошибок

Как извлечь все цифры из строки и получить число

Частая практическая задача — вытащить число из смешанной строки: «Коробка 25 шт», «Арт. 001234», «Накладная № 56 от поставщика». Решение — собрать все цифровые символы в отдельную строку, а затем преобразовать её в число.

Функция ИзвлечьЧислоИзСтроки(ИсходнаяСтрока) Экспорт

Цифры = "0123456789";

Результат = "";

Для Позиция = 1 По СтрДлина(ИсходнаяСтрока) Цикл

Символ = Сред(ИсходнаяСтрока, Позиция, 1);

Если СтрНайти(Цифры, Символ) > 0 Тогда

Результат = Результат + Символ;

КонецЕсли;

КонецЦикла;

Если Результат = "" Тогда

Возврат 0;

КонецЕсли;

Возврат Число(Результат);

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

Здесь есть важное ограничение: функция склеивает все цифры подряд. Из строки «Заказ 12 от 05.03» получится число 120503, а не 12 и не 5. Если в строке может быть несколько числовых групп и нужна только одна, останавливайте цикл после первой завершённой группы цифр или разбивайте строку по разделителям через СтрРазделить().

Ещё одна ловушка — преобразование Число(). Если собранная строка слишком длинная, произойдёт переполнение или потеря точности. Для номеров телефонов, ИНН, длинных артикулов не преобразуйте результат в число, а оставляйте строкой: ведущие нули в «001234» при преобразовании в число безвозвратно теряются.

Как найти цифру в строке запросом через ПОДОБНО

Когда цифры нужно искать в таблице — например, отобрать все наименования номенклатуры, содержащие номера, — перебор в коде неэффективен. Правильное решение — оператор ПОДОБНО в языке запросов с шаблоном, содержащим список символов в квадратных скобках.

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

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

"ВЫБРАТЬ

| Номенклатура.Ссылка КАК Ссылка,

| Номенклатура.Наименование КАК Наименование

|ИЗ

| Справочник.Номенклатура КАК Номенклатура

|ГДЕ

| Номенклатура.Наименование ПОДОБНО ""%[0-9]%""";

Шаблон "%[0-9]%" читается так: любые символы, затем одна цифра из диапазона 0–9, затем снова любые символы. Символ процента заменяет любую последовательность, включая пустую, поэтому условие найдёт цифру в любой позиции строки. Конструкция [0-9] — это список допустимых символов, аналог класса в регулярных выражениях.

У ПОДОБНО есть ограничения: сравнение регистронезависимо для букв, а сама операция на больших таблицах не использует индексы и приводит к полному сканированию. Для разового отбора это приемлемо, но в регулярно выполняемых отчётах по миллионам записей лучше хранить признак наличия цифр в отдельном реквизите и заполнять его при записи объекта.

Сравнение вариантов

Перебор символов в коде

Универсально, работает везде, позволяет получить позицию и извлечь цифры. Медленно при массовой обработке таблиц.

ПОДОБНО в запросе

Оптимально для отбора строк в таблицах. Даёт только факт наличия, без позиции и извлечения.

Регулярные выражения через COM/VBScript

Гибкий поиск сложных шаблонов, но работает только на Windows-клиенте с установленным компонентом. Не подходит для сервера Linux.

Как использовать регулярные выражения и внешние средства

Полноценных встроенных регулярных выражений в языке 1С нет. На Windows-клиенте их можно получить через COM-объект VBScript.RegExp, что удобно для сложных шаблонов: например, «три цифры подряд» или «цифра после буквы».

RegExp = Новый COMОбъект("VBScript.RegExp");

RegExp.Pattern = "\d";

RegExp.Global = Истина;

Если RegExp.Test("Артикул А123") Тогда

Сообщить("Цифра найдена");

КонецЕсли;

Шаблон \d означает любую цифру. Однако у этого подхода жёсткое ограничение: COM-объекты доступны только под Windows и не работают на сервере Linux, в веб-клиенте и на мобильной платформе. Если код должен выполняться на сервере в кластере с Linux, вариант с VBScript отпадает сразу.

Кроссплатформенная альтернатива — внешние компоненты по технологии Native API или вынос проверки на сторону СУБД через запрос. На практике для задачи «найти цифру в строке» возможностей перебора и ПОДОБНО достаточно в подавляющем большинстве случаев, и усложнять архитектуру ради регулярных выражений не стоит.

Типичные ошибки
01
Использование Найти() вместо СтрНайти() в новых конфигурациях — код работает, но выдаёт предупреждения при проверке и считается устаревшим
02
Преобразование извлечённых цифр в Число для ИНН и номеров счетов — теряются ведущие нули, данные искажаются
03
Проверка только первого символа строки вместо полного перебора — цифры в середине и конце не обнаруживаются
04
Использование ПОДОБНО без символов % по краям шаблона — найдутся только строки, целиком состоящие из цифр
05
Забытая проверка результата поиска позиции на 0 — Сред() с нулевой позицией даёт ошибку или неожиданный результат

Как проверить результат и отладить функцию

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

Пустая строка заслуживает отдельного внимания: цикл Для Позиция = 1 По 0 не выполнится ни разу, и функция корректно вернёт «цифр нет». Это нормальное поведение, но если дальше по коду результат используется для поиска в базе, убедитесь, что пустой ввод обрабатывается осознанно, а не молча проглатывается.

Для отладки в конфигураторе поставьте точку останова внутри цикла и смотрите значения переменных Символ и Позиция в табло. Если функция используется в обработке больших таблиц, замерьте время выполнения на реальном объёме данных через ТекущаяУниверсальнаяДатаВМиллисекундах() до и после цикла — так вы заранее поймёте, нужна ли оптимизация запросом.

Контрольные точки

Как проверить результат

Строка без цифр, например «Просто текст»
Норма

Функция возвращает Ложь или позицию 0

Тревожный признак

Возвращается Истина — проверьте строку с цифрами в коде на опечатки

Пустая строка
Норма

Корректный возврат «нет цифр» без ошибок

Тревожный признак

Ошибка выполнения или зависание

Строка «001234» после извлечения
Норма

Получено строковое «001234» или осознанное число 1234

Тревожный признак

Число 1234 там, где важны ведущие нули

Запрос с ПОДОБНО на тестовой таблице
Норма

В выборку попали строки с цифрой в любой позиции

Тревожный признак

Попали только строки из одних цифр — потеряны символы % в шаблоне

Если проверка на цифры нужна постоянно (например, валидация артикулов при записи), вынесите функцию в общий серверный модуль с признаком «Вызов сервера». Это избавит от дублирования кода в десятках мест и упростит исправления: менять логику придётся только в одном модуле.
ПЗ
Практическое замечание

Часто задаваемые вопросы

Как проверить, что строка состоит только из цифр?

Используйте тот же перебор, но с обратным условием: если встретился символ, которого нет в строке «0123456789», сразу возвращайте Ложь. Если цикл завершился без таких символов — строка полностью цифровая. Пустая строка при этом формально пройдёт проверку, поэтому при необходимости добавьте отдельную проверку на пустоту через ПустаяСтрока().

Чем СтрНайти отличается от Найти?

Функционально это одно и то же: обе функции возвращают позицию подстроки или 0. СтрНайти() появилась в платформе 8.3.6 как часть нового семейства строковых функций, а Найти() считается устаревшей и при проверке конфигурации выдаёт замечания. В новом коде используйте СтрНайти(), в старом режиме совместимости — Найти().

Как найти в строке не цифру, а букву или спецсимвол?

Механизм тот же: замените строку-алфавит «0123456789» на нужный набор символов, например «0123456789.,;» для поиска цифр и знаков препинания, или строку с буквами алфавита. Для проверки «символ является буквой» удобнее сравнивать код символа через КодСимвола() с диапазонами кодов нужного алфавита.

Работает ли ПОДОБНО с шаблоном [0-9] во всех СУБД?

Оператор ПОДОБНО со списком символов в квадратных скобках — часть языка запросов 1С, и платформа транслирует его в поддерживаемые СУБД. На практике шаблоны с диапазонами корректно работают на основных поддерживаемых базах. Если сомневаетесь, проверьте запрос на тестовой выборке именно на вашей СУБД перед промышленным запуском.

Как извлечь из строки только первое число, если чисел несколько?

Ведите в цикле два признака: «число началось» и «число закончилось». Накапливайте цифры, пока они идут подряд, и прерывайте цикл, когда после начатого числа встретился нецифровой символ. Так из строки «Заказ 12 от 05.03» будет извлечено именно 12, а не склейка всех цифр.

Почему перебор символов медленно работает на больших таблицах?

Каждая строка таблицы обрабатывается посимвольно в коде, а это тысячи вызовов функций на запись. При объёмах в сотни тысяч строк переносите фильтрацию на уровень запроса через ПОДОБНО либо храните заранее вычисленный признак в отдельном реквизите и индексируйте его.

Итог

Что важно запомнить

Цифру в строке в 1С ищут перебором символов с проверкой через СтрНайти("0123456789", Символ) — это даёт факт наличия, позицию и возможность извлечь число. Для отбора в таблицах используйте ПОДОБНО "%[0-9]%" в запросе. Не преобразуйте в число строки с ведущими нулями и всегда проверяйте функцию на пустых строках и граничных случаях.