Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Firebird, InterBase Новый топик    Ответить
Топик располагается на нескольких страницах: 1 2      [все]
 Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
Простой пример с регулярным выражением, используемым для проверки FQDN:
SELECT _ASCII 'localh' SIMILAR TO
    '([a-zA-Z0-9]{1,63}.|[a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9].)*([a-zA-Z0-9]{1,63}|[a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9]).?'
  FROM rdb$database
Если один символ ASCII проверяется около 49 наносекунд, то каждый следующий символ увеличивает время выполнения ВДЕСЯТЕРО. Так обработка строки из шести символов занимает уже около 4,9 секунд.
3 июн 19, 14:47    [21900554]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
hvlad
Member

Откуда:
Сообщений: 10531
Когда пишут о регрессии, то обычно что-то с чем-то сравнивают
3 июн 19, 14:54    [21900561]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
rdb_dev, причём, если короткие последовательности символов ASCII разделены точками, то скорость обработки всего выражения значительно быстрее. К примеру:
SELECT _ASCII 'local.mat.ego.host' SIMILAR TO
    '([a-zA-Z0-9]{1,63}.|[a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9].)*([a-zA-Z0-9]{1,63}|[a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9]).{0,1}'
  FROM rdb$database
выполняется около 47мс, тогда как:
SELECT _ASCII 'local.mat.ego.host' SIMILAR TO
    '([a-zA-Z0-9]{1,63}.|[a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9].)*([a-zA-Z0-9]{1,63}|[a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9]).{0,1}'
  FROM rdb$database
выполняется уже около 470мс
3 июн 19, 15:08    [21900585]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
Пардон! В последнем операторе должно быть _ASCII 'local'
3 июн 19, 15:09    [21900589]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
Скорость обработки строки с разделёнными точками именами приблизительно равна скорости обработки самого короткого имени между точками.
3 июн 19, 15:37    [21900615]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
bsv9
Member

Откуда:
Сообщений: 33
С регулярными вфражениями в FB все очень плохо. http://tracker.firebirdsql.org/browse/CORE-5854
3 июн 19, 15:50    [21900634]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
Симонов Денис
Member

Откуда: Рязань
Сообщений: 9831
rdb_dev,

ты ответ Влада то прочитал? Регрессия по сравнению с чем? Где сравнительные тесты 2.5, 3.0?
3 июн 19, 15:51    [21900637]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
WildSery
Member

Откуда: да, оттуда.
Сообщений: 16403
Симонов Денис,

Перевожу: регрессия ожиданий. Думал что будет "ооо!", а оно "нуууу".
3 июн 19, 15:56    [21900642]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
Симонов Денис
rdb_dev,

ты ответ Влада то прочитал? Регрессия по сравнению с чем? Где сравнительные тесты 2.5, 3.0?
На 2.5, вроде бы, такого не замечал. Даже если сравнивать скорость обработки строк: 'local.host', 'local' и 'hostname.domain.my' то последнее выполнится быстрее всего, а следовательно, регрессия налицо даже без сравнения с другими версиями.
3 июн 19, 15:57    [21900645]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
WildSery
Симонов Денис,

Перевожу: регрессия ожиданий. Думал что будет "ооо!", а оно "нуууу".
Не так! Оно "ой-йо-о-о-о-о-о..."
3 июн 19, 15:58    [21900647]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
hvlad
Member

Откуда:
Сообщений: 10531
bsv9
С регулярными вфражениями в FB все очень плохо. http://tracker.firebirdsql.org/browse/CORE-5854
Прям всё ? Или ВСЁ ?! :)
И зачем постить ссылку на тикет, закрытый как дубликат ?
3 июн 19, 16:00    [21900652]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
hvlad
Member

Откуда:
Сообщений: 10531
rdb_dev
регрессия налицо
Непонимание употребляемых слов - вот что на лице.

PS проблему с быстродействием SIMILAR TO в некоторых случаях никто не отрицает
3 июн 19, 16:05    [21900662]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
hvlad
PS проблему с быстродействием SIMILAR TO в некоторых случаях никто не отрицает
Ясно! Чо делать-то? :)
3 июн 19, 16:14    [21900674]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
Dimitry Sibiryakov
Member

Откуда:
Сообщений: 48163

rdb_dev
Чо делать-то? :)

Вариант 1: Открыть исходники, исправить, запуллить реквест.
Вариант 2: Забыть о существовании регэкспов.

Posted via ActualForum NNTP Server 1.5

3 июн 19, 16:20    [21900680]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
bsv9
Member

Откуда:
Сообщений: 33
hvlad
И зачем постить ссылку на тикет, закрытый как дубликат ?

В оригинальном тикете слишком много кода. В этом тикете, по моему, понятнее показана проблема - на примере одного регекспа. Проблема с регулярными выражениями началась в FB 3. И до сих пор не решена. Не аккуратно написанное выражение может очень-очень надолго завесить серевер со 100% утилизацией процессора. Например, вот это:
select iif ('abcde.abc' similar to '[[:ALPHA:].]{1,60}.ab' ,1,0) is_similar from rdb$database 

В 2.5 таких проблем не было.
3 июн 19, 16:26    [21900688]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
hvlad
Member

Откуда:
Сообщений: 10531
rdb_dev
hvlad
PS проблему с быстродействием SIMILAR TO в некоторых случаях никто не отрицает
Ясно! Чо делать-то? :)
1. Пинать трекер
2. Взять готовую udf, правда там скорее всего будет POSIX синтаксис regexp'ов, а он отличается от SQL варианта
3. Улучшить реализацию в FB, там нет ничего военного и в инете куча кода для regexp'ов.
Единственная сложность - отличие POSIX и SQL синтаксиса
3 июн 19, 16:29    [21900692]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
hvlad
Member

Откуда:
Сообщений: 10531
bsv9
Проблема с регулярными выражениями началась в FB 3...
...В 2.5 таких проблем не было
Очень сомневаюсь. Я не помню, чтобы в 3-ке трогали этот код.
Если же это действительно так, то имеет смысл опять же пинать трекер.
Но с аргументами.
3 июн 19, 16:30    [21900693]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
bsv9
Member

Откуда:
Сообщений: 33
hvlad
Очень сомневаюсь. Я не помню, чтобы в 3-ке трогали этот код.

Хм, дейстивтельно, FB 2.5 так же глухо зависает.
3 июн 19, 16:39    [21900699]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
WildSery
Member

Откуда: да, оттуда.
Сообщений: 16403
rdb_dev
регрессия налицо даже без сравнения с другими версиями.
Записал в блокнотик.
4 июн 19, 09:29    [21901181]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
WildSery, а определения "линейная зависимость" и "линейная функция" в твоём блокнотике уж есть? 😏
4 июн 19, 09:50    [21901200]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
WildSery
Member

Откуда: да, оттуда.
Сообщений: 16403
rdb_dev,

Для таких банальностей и гугль сойдёт.
4 июн 19, 10:08    [21901223]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
Ещё немного поисследовал проблему... Оказалось, что "SIMILAR TO" очень капризен не только к сложным выражениям, но и к символам, отсутствующим в лидирующих вариациях паттернов, указанных в выражении через "|". Так например простое выражение:
'([a-zA-Z0-9]{1,63})|([a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9])'
на строку 'local-host' будет зверски тупить, тогда как:
'([a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9])|([a-zA-Z0-9]{1,63})'
отработает ожидаемо быстро. Если же вовсе встретиться незнакомый паттернам символ в строке из более чем восьми символов, можно смело килять процесс сервера, так как ФБ затупит на сотни, а то и тысячи секунд и его невозможно будет остановить штатно через запуск/остановку служб.

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

SET TERM ^;
CREATE OR ALTER FUNCTION FQDN__CHECK
  (
    fqdName ASCII_STRING DEFAULT NULL
  )
  RETURNS BOOLEAN
AS
  DECLARE VARIABLE dot      INT64;
  DECLARE VARIABLE dotPart  ASCII_STRING;
  DECLARE VARIABLE dotTail  ASCII_STRING DEFAULT NULL;
  DECLARE VARIABLE regEx    ASCII_STRING
    DEFAULT '([a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9])|([a-zA-Z0-9]{1,63})'
BEGIN
  IF (:fqdName IS NULL) THEN RETURN NULL;
  IF (NOT :fqdName SIMILAR TO '[a-zA-Z0-9-.]{1,255}') THEN RETURN FALSE;

  dotTail = fqdName;
  WHILE (:dotTail IS NOT NULL) DO
    BEGIN
      dot = Position('.', dotTail);
      IF (:dot = 0) THEN
        BEGIN
          dotPart = dotTail;
          dotTail = NULL;
        END
      ELSE
        BEGIN
          dotPart = Left(dotTail, dot - 1);
          IF (Char_Length(:dotTail) = :dot) THEN
            dotTail = NULL;
          ELSE
            dotTail = Substring(dotTail FROM dot + 1);
        END
      IF (NOT :dotPart SIMILAR TO :regEx) THEN RETURN FALSE;
    END
  RETURN TRUE;
END^
SET TERM ;^

7 июн 19, 11:20    [21904326]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
Tonal
Member

Откуда: Новосибирск
Сообщений: 168
Похоже проще написать UDF/R-ку в коей использовать любую удобную реализацию регулярок.
Например из ICU, которая и так используется сервером. :)

Собственно в коде сервера можно было бы именно её и вызвать, предварительно странслировав синтаксис, если нужно. :)
7 июн 19, 12:41    [21904421]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
rdb_dev
Member

Откуда: с болот
Сообщений: 2929
Рано я обрадовался, что нашёл решение... Оказалось, что при экранировании неразрешённых символов, поток сервера вешается от неизвестного символа '+' даже на элементарнейшем паттерне:
'my-host.my-domain.org+.ru' SIMILAR TO '[-.a-zA-Z0-9]{1,255}'
+ Пришлось переписать функцию
SET TERM ^;
CREATE OR ALTER FUNCTION FQDN__CHECK
  (
    fqdName ASCII_STRING DEFAULT NULL
  )
  RETURNS BOOLEAN
AS
  DECLARE VARIABLE dot    INT64;
  DECLARE VARIABLE part   ASCII_STRING;
  DECLARE VARIABLE tail   ASCII_STRING DEFAULT NULL;
  DECLARE VARIABLE regEx  ASCII_STRING
    DEFAULT '([a-zA-Z0-9][a-zA-Z0-9-]{0,61}[a-zA-Z0-9])|([a-zA-Z0-9]{1,63})';
  DECLARE VARIABLE permitted CHAR(38) CHARACTER SET ASCII
    DEFAULT 'ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789-.';
BEGIN
  IF (:fqdName IS NULL) THEN RETURN NULL;
  tail = Upper(fqdName);
  dot = Char_Length(tail);
  IF (:dot = 0) THEN RETURN FALSE;
  WHILE (:dot != 0) DO
    IF (Position(Substring(:tail FROM :dot FOR 1), :permitted) = 0) THEN
      RETURN FALSE;
    ELSE
      dot = dot - 1;

  WHILE (:tail IS NOT NULL) DO
    BEGIN
      dot = Position('.', tail);
      IF (:dot = 0) THEN
        BEGIN
          part = tail;
          tail = NULL;
        END
      ELSE
        BEGIN
          part = Left(tail, dot - 1);
          IF (Char_Length(:tail) = :dot) THEN
            tail = NULL;
          ELSE
            tail = Substring(tail FROM dot + 1);
        END
      IF (NOT :part SIMILAR TO :regEx) THEN RETURN FALSE;
    END
  RETURN TRUE;
END^
SET TERM ;^
7 июн 19, 13:17    [21904459]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
Tonal
Member

Откуда: Новосибирск
Сообщений: 168
Если смотреть по коду (SimilarToMatcher.h), то конструкция x{n,m} преобразуется в x{n}(x?){m-n}.
Что вызывает комбинаторный взрыв при неудаче.
Так что просто не пользуйся конструкцией повторения.
7 июн 19, 13:50    [21904488]     Ответить | Цитировать Сообщить модератору
 Re: Серьёзная регрессия регулярных выражений в FB4.0  [new]
hvlad
Member

Откуда:
Сообщений: 10531
Особо страждущие могут попробовать вот эту сборку fb4

https://ci.appveyor.com/api/buildjobs/pljaus5svx65kafk/artifacts/output.zip

здесь для regexp используется библиотека RE2
26 авг 19, 10:02    [21957494]     Ответить | Цитировать Сообщить модератору
Топик располагается на нескольких страницах: 1 2      [все]
Все форумы / Firebird, InterBase Ответить