Подтвердить что ты не робот

Регулярное выражение для поиска двух строк в любом месте ввода

Как написать регулярное выражение для соответствия двум заданным строкам в любой позиции в строке?

Например, если я ищу cat и mat, он должен соответствовать:

The cat slept on the mat in front of the fire.
At 5:00 pm, I found the cat scratching the wool off the mat.

Независимо от того, что предшествует этим строкам.

4b9b3361

Ответ 1

/^.*?\bcat\b.*?\bmat\b.*?$/m

Использование модификатора m (который гарантирует, что метасимволы начала/конца совпадают по разрыву строки, а не в самом начале и в конце строки):

  • ^ соответствует началу строки
  • .*? соответствует любому символу строки до...
  • \b соответствует границе слова первое вхождение границы слова (в связи с обсуждением @codaddict)
  • затем строку cat и другую границу слова; обратите внимание, что символы подчеркивания рассматриваются как "слова", поэтому _cat_ не будет соответствовать *;
  • .*?: любые символы до...
  • mat, граница
  • .*?: любые оставшиеся символы до...
  • $: конец строки.

Важно использовать \b, чтобы гарантировать, что указанные слова не являются частью более длинных слов, и важно использовать не-жадные подстановочные знаки (.*?) по сравнению с жадным (.*), потому что последний будет терпеть неудачу такие строки, как "На вершине коврика под кошкой есть кошка". (Это будет соответствовать последнему появлению "кошки", а не первого.)

* Если вы хотите иметь возможность сопоставлять _cat_, вы можете использовать:

/^.*?(?:\b|_)cat(?:\b|_).*?(?:\b|_)mat(?:\b|_).*?$/m

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

Изменить: в комментариях был поднят вопрос о том, будет ли решение работать для фраз, а не просто слов. Ответ таков: "Да. Следующее будет соответствовать строке" A, которая включает в себя как первую фразу, так и вторую фразу":

/^.*?(?:\b|_)first phrase here(?:\b|_).*?(?:\b|_)second phrase here(?:\b|_).*?$/m

Изменить 2: Если заказ не имеет значения, вы можете использовать:

/^.*?(?:\b|_)(first(?:\b|_).*?(?:\b|_)second|second(?:\b|_).*?(?:\b|_)first)(?:\b|_).*?$/m

И если производительность действительно является проблемой здесь, возможно, это будет выглядеть (если ваш механизм regex поддерживает его) может (но, вероятно, не будет) работать лучше, чем выше, но я оставлю как более сложную обзорную версию, так и тестирование производительности в качестве упражнения для респондента/читателя.

Отредактировано за комментарий @Alan Moore. У меня не было возможности проверить это, но я возьму ваше слово за это.

Ответ 2

(.* word1.* word2.* )|(.* word2.* word1.*)

Ответ 3

Если вам абсолютно необходимо использовать только одно регулярное выражение, то

/(?=.*?(string1))(?=.*?(string2))/is

i modifier = нечувствительность к регистру

. *? Ленивая оценка для любого персонажа (совпадения как можно меньше)

? = для положительного LookAhead он должен соответствовать где-то

s modifier =. (period) также принимает разрывы строк

Ответ 4

Вы можете попробовать:

\bcat\b.*\bmat\b

\b является якорем и соответствует границе слова. Он будет искать слова кошку и коврик в любой точке строки с ковриком, следующим за кошкой. Он не будет соответствовать:

Therez caterpillar on the mat.

но будет соответствовать

The cat slept on the mat in front of the fire

Если вы хотите сопоставить строки, у которых буквы, а затем мат, вы можете попробовать:

cat.*mat

Это будет соответствовать обеим приведенным выше примерам.

Ответ 5

Это достаточно легко при обработке требуемой мощности:

(string1(.|\n)*string2)|(string2(.|\n)*string1)

Я использовал это в visual studio 2013, чтобы найти все файлы, в которых были как строки 1, так и 2.

Ответ 6

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

>>> for line in open("file"):
...     g=0;f=0
...     s = line.split()
...     for item in s:
...         if item =="cat": f=1
...         if item =="mat": g=1
...     if (g,f)==(1,1): print "found: " ,line.rstrip()

found:  The cat slept on the mat in front of the fire.
found:  At 5:00 pm, I found the cat scratching the wool off the mat.

Ответ 7

Это работает для поиска файлов, содержащих как String1, так и String2

(((|.\П)) String1 ((|.\П)) String2) | (((|.\П)) String2 ((|.\П)) String1)

Соответствует любому количеству символов или строкам поля а затем String1 за которым следует любое количество символов или полей строки а затем String2 ИЛИ Сопоставьте любое количество символов или полей строки а затем String2 за которым следует любое количество символов или полей строки а затем String1