Избегайте извлечения слова с определенным термином

#regex #regex-group

#регулярное выражение #регулярное выражение-группа

Вопрос:

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

Тестовая строка:

 tag=os index=linux index=windows NOT index=mac tag=db index="a_something-else" NOT   index=solaris
  

Текущее (сбой) выражение регулярного выражения:

 index=(")?(?<my_indexes>w (-)?(w )?)(")?
  

Это регулярное выражение извлекает все index=zyx слова. Но следует избегать случая, NOT например NOT index=mac , или NOT index=solaris . Например. результаты должны быть такими:

 index=linux
index=windows
index="a_something-else"
  

Есть предложения?

Комментарии:

1. Из какой среды вы запускаете свое регулярное выражение? Использование отрицательного внешнего вида переменной длины сделало бы решение вашей проблемы тривиальным, но это не реализовано в большинстве вариантов регулярных выражений

2. @Aaron это будет Splunk. Он использует PCRE. Ссылка: docs.splunk.com/Documentation/Splunk/8.0.6/SearchReference/Rex

3. Тогда он должен разрешать поиск с переменной шириной, и простое добавление префикса к вашему регулярному (?<!NOTs ) выражению должно сделать свое дело, оно проверяет, что тому, что ему соответствует, не предшествует «NOT», за которым следует любое количество пробелов

Ответ №1:

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

Затем вы можете сделать двойные кавычки необязательными внутри группы захвата и ссылаться на нее с помощью 1 и 2

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

 bNOTh index=("?)w (?:-w )*1(*SKIP)(*FAIL)|index=("?)w (?:-w )*2
  

Объяснение

  • bNOTh Сопоставьте символы NOT и 1 горизонтальных пробелов
  • index=("?) Сопоставьте index= и зафиксируйте необязательное " значение в группе 1
  • w (?:-w )*1 Сопоставьте символы 1 word, необязательно повторяющиеся, - и символы 1 word. Затем обратная ссылка на то, что записано в группе 1
  • (*SKIP)(*FAIL)| Пропустить совпадение
  • index=("?) Сопоставьте index= и зафиксируйте необязательное " значение в группе 2
  • w (?:-w )*2 То же, что и предыдущий шаблон выше, теперь с обратной ссылкой на группу 2

Демонстрация регулярных выражений

Если вам не нужны двойные кавычки a_something-else и требуется только значение после = , вы можете использовать другую группу захвата или использовать именованную группу захвата my_indexes

 bNOTh index=("?)w (?:-w )*1(*SKIP)(*FAIL)|index=("?)(?<my_indexes>w (?:-w )*)2
  

Демонстрация регулярных выражений