Opened 4 years ago

Last modified 16 months ago

#554 closed дефект

РЭ: ошибки в примерах регулярных выражений — at Version 3

Reported by: alx Owned by: Vladimir
Priority: major Component: Руководство по эксплуатации
Keywords: Cc:

Description (last modified by alx)

В РЭ аппаратуры MC04-DSL-3U редакции 40 в таблице 7.1 на странице 195 даны некоторые примеры регулярных выражений с комментариями. К сожалению, некоторые из них содержат ошибки.

^537$» Символ доллара в регулярном выражении совпадает с концом строки, что означает, что после предыдущего символа 7 никаких других символов в номере быть не должно. Однако далее в регулярном выражении стоит символ закрывающих кавычек, который требует, чтобы этот символ был в номере после символа 7. Как результат этого противоречия, такое регулярное выражение никогда не будет совпадать ни с одной строкой. Предполагаю, что символ '»' в регулярное выражение добавлен по ошибке и предлагаю его убрать.

.{4}» В описании этого примера написано: "4 любых символа, например, 123#". Это не совсем так: данное регулярное выражение требует, чтобы после любых четырех символов непременно следовал символ '»'. Например оно будет совпадать со строками Станция «Мир», 1234»лабуда, но не будет совпадать со строками Навальный или Путин, хотя в последних имеется четыре символа. Предлагаю либо добавить в описание примера уточнение ", за которыми следует символ '»'", либо убрать символ '»' из регулярного выражения.

^2\d{6} В описании этого примера сказано: "номер длиной не менее 7 цифр и начинается с цифры 2". Описание не совсем точное, так как не очень внимательный читатель может понять его как "любое число цифр, но не менее 7, начинающийся с 2", хотя на самом деле после 7 цифр могут следовать любые символы, что верно показано в примере далее. Предлагаю переформулировать описание примерно так: "номер, начинающийся с цифры 2, за которой следуют 6 любых цифр, за которыми могут следовать любые другие символы".

^(?![3,4]0\d{2})\d* С этим примером сразу несколько проблем. Во-первых, оно оканчивается на \d*, что означает любое количество цифр (включая нулевое). Но, так как в регулярном выражении нет символа '$' (конец строки), после этих цифр строка может содержать любые другие символы, в том числе и опять цифры! Таким образом, фрагмент \d* в данном выражении не имеет никакого эффекта, и может быть удален. Поэтому предлагаю не учить читателя плохому, а сразу удалить этот фрагмент из примера, сделав пример более простым для чтения и понимания: ^(?![3,4]0\d{2}). Во-вторых, в описании к примеру написано: "принимает все вызовы кроме номеров начинающихся на 30хх, 40хх". Это неверно. Как раз 30xx и 40xx будут приниматься (совпадают с регулярным выражением), потому что данное регулярное выражение имеет следующий смысл: совпадает со всем кроме начинающегося с одного из символов "три" ('3'), "запятая" (',') или "четыре" ('4'), за которым следует символ '0', за которым следуют две любые цифры. Символ же 'x' цифрой не является. Да, я догадался, что под символом 'x' подразумевалась цифра, но у читателя, незнакомого с регулярными выражениями (а иначе ему не нужен этот раздел), оснований для такой догадки нет, и он будет воспринимать все написанное буквально! Предлагаю приведенную мной формулировку и записать в качестве пояснения. И привести такие примеры: "Например не будут приниматься вызовы номеров '3074', ',039', '4081'".

^[3,4]0\d{2}$ В описании написано: "принимает вызовы только на номера вида 30хх, 40хx". Здесь в описании та же проблема, что и в предыдущем примере. Предлагаю переформулировать описание примерно так: принимает только вызовы номеров, начинающихся с одного из символов "три" ('3'), "запятая" (',') или "четыре" ('4'), второй символ которых "ноль" ('0'), за которым следует ровно две любые цифры. Например '3074', ',039', '4081'.

/^2(\d{6})/83422\1 Во-первых, стоит, наверное, во вводной части уточнить, что ряд конфигурационных параметров поддерживает специальную форму записи - регулярное выражение с заменой, иначе неискушенный читатель подумает, что такая форма - часть синтаксиса PCRE. На самом деле это не так, такая форма записи - наше собственное изобретение. Во-вторых, в описании к примеру написано: "номер из 7 цифр, начинающийся с цифры 2". Это не совсем точно. Более точным будет "из 7 цифр, за которыми могут следовать любые символы".

Change History (3)

comment:1 by san, 4 years ago

Вот текст с учётом замечаний Алексея:


  • Рег. выражение вызова – настройка коммутации вызовов в данное окончание.

При обслуживании вызова, после проверки совпадений вызываемого номера с номерами
канальных окончаний, если совпадений обнаружено не было, выполняется второй проход,
на котором к номеру(username) вызываемого абонента применяется регулярное
выражение. Вызов будет передан для обслуживания первому незанятому канальному
окончанию, у которого задано регулярное выражение вызова, под которое подпадает
вызываемый номер. Примеры:

  • . - номер содержит хотя-бы 1 символ, любой (при задании такого выражения в качестве "Рег. выражение вызова", окончание будет принимать любые вызовы);
  • 555 - окончание будет принимать вызовы на любой номер содержащий 555, например: 83455567, 555123, 123555.
  • ^5 - номер начинается с пятёрки, окончание будет принимать вызовы только на номера начинающиеся с цифры 5 (символ ^ в выражении обозначает начало номера);
  • ^537 - номер начинается с 537;
  • ^537$ - только номер 537;
  • .{4} - 4 любых символа, например 123#;
  • ^2\d{6}$ - номер длиной ровно 7 цифр и начинается с цифры 2, например 2123456(символ $ в выражении обозначает конец номера);
  • ^2\d{6} - номер, начинающийся с цифры 2, за которой следуют 6 любых цифр, за которыми могут следовать любые другие символы, например 2123456#789;
  • ^(?![34]0\d{2}) - принимает вызовы на все номера, кроме начинающихся с 30 или 40, за которыми следуют две любые цифры. Например не будут приниматься вызовы номеров '3014', '4099';
  • ^[34]0\d{2}$ - принимает только вызовы номеров, начинающихся с последовательности цифр 30 или 40, за которым следует ровно две любые цифры. Например '3074', '4081';
  • ^8(?!10)\d{10}$ - междугородние номера длиной 11 цифр, начинающиеся с 8, исключая международные, начинающиеся с 810;
  • /^5(\d{3})/6\1 - регулярное выражение с заменой - имеет формат /<выражение>/<замена>, где 'выражение' - регулярное выражение, 'замена' - строка, на которую заменяется вызываемый номер в случае его совпадения с регулярным выражением. 'Замена' может содержать подстановки фрагментов регулярного выражения '\1', '\2' и т.д. В данном примере 'выражение'- ^5(\d{3}), а 'замена' - 6\1. В случае совпадения номера с выражением ^5(\d{3})(цифра 5, затем три цифры за которыми следуют любые символы), окончание принимает вызов, и из номера удаляются все символы кроме трёх цифр следовавших за префиксом '5', затем к номеру добавляется новый префикс '6'. Т.е. вызов на номер 5205 будет принят окончанием и отправлен в сторону TDM на номер 6205;

comment:2 by Vladimir, 4 years ago

Resolution: готово
Status: newclosed

В РЭ-41 вставил текст из "comment:1 Changed 7 недель ago by san"
(т.к. замечаний и возражений по тексту от san нет).

comment:3 by alx, 4 years ago

Description: modified (diff)
Resolution: готово
Status: closedreopened

Я считаю, что когда что-то кому-то объясняешь, пример должен иллюстрировать объяснение, дополнять его, помогая лучшему пониманию, но не заменять его.

Когда я предлагал пример для описания регулярного выражения ^(?![3,4]0\d{2})\d*, я предложил дополнить описание этого выражения примером, а не оставить один только пример вместо описания. Александр в своем комментарии также предлагал перед примером номеров, вызовы которых не будут приниматься, описать смысл выражения. Однако в тексте РЭ редакции 42 в таблице все объяснение состоит только из примера двух номеров, вызовы которых не будут приниматься. Считаю это неправильным, так как по двум частным случаям трудно понять общий принцип.

Предлагаю дополнить пример в описании регулярного выражения ^(?![34]0\d{2}) общим описанием его смысла (или вообще исключить это выражение из таблицы, так как без общего описания не вижу смысла в примере).

Здесь же в описании регулярного выражения с заменой ^/^2(\d{6})/83422\1 говорится: "В данном примере 'выражение'- ^5(\d{3}), а 'замена' – 6\1". Это совершенно неверно, так как на самом деле здесь регулярное выражение (то, что расположено между двумя символами '/') - ^2(\d{6}), строка замены - 83422\1. Ну и далее неоднократно упоминается то же выражение и цифра '5', которой вообще нет ни в собственно регулярном выражении, ни в строке замены. Предлагаю исправить описание.

Обратите внимание, что когда я предлагал дополнить описание последнего выражения фразой "и из номера удаляются все символы кроме первых семи", я был неправ: строкой, состоящей из префикса 8342 и первых семи цифр вызываемого номера, будет заменена только та часть вызываемого номера, которая совпадает с регулярным выражением, то есть как раз первые семь цифр. Все, что в номере вызываемого есть после этих семи цифр, останется в неизменном виде. То есть никакие цифры из номера удаляться не будут! Описание тикета исправил.

Note: See TracTickets for help on using tickets.