我有以下字符串,我尝试将相应的'foo'中的字符串与'bar = 1','bar = 2'或'bar = 3'匹配。所以一次只能匹配一次。
file_header
foo lorem ipsum \pope
24 dolor sit amet, consectetur adipisici elit
Excepteur sint obcaecat cupiditat non
gnu blu bar=1
foo lorem ipsum \
@>@!@ consectetur adipisici elit
gnu blu bar=2
foo lorem ipsum
23 dolor sit amet, consectetur adipisici elit
gnu blu bar=3
foo ... etc
我尝试了所有内容,从简单的^foo.*?bar=2$
到类似^(?!\bfoo\b.*\bfoo\b).*\bfoo\b.*bar=2$
的内容。但是在激活multiline和dotall的情况下,它将始终匹配第一个'foo'或甚至标记整个文件头。 :(
使用multiline和dotall时,似乎不可能出现非贪婪的行为。
答案 0 :(得分:1)
您可以使用像
这样的驯化贪婪令牌^foo(?:(?!^foo|bar=2$).)*bar=2$
(?:(?!^foo|bar=2$).)*
匹配任何非foo
的文本(在行/字符串的开头),而不是行/字符串末尾的bar=2
。
请参阅regex demo。但是,这样的构造是消耗资源的,建议将其展开。这是一个选项:
^foo[^\nb]*(?:\n(?!foo)[^\nb]*|b(?!ar$)[^\nb]*)*bar=2$
请参阅another demo。
答案 1 :(得分:1)
此程序查找AxisView
的所有非重叠事件。请注意使用此表达式在foo <stuff> bar=<number>
- 模式下成功使用非贪婪运算符:re.MULTILINE
^foo.*?bar=\d+$
结果:
import re
from pprint import pprint
data = '''
file_header
foo lorem ipsum \pope
24 dolor sit amet, consectetur adipisici elit
Excepteur sint obcaecat cupiditat non
gnu blu bar=1
foo lorem ipsum \
@>@!@ consectetur adipisici elit
gnu blu bar=2
foo lorem ipsum
23 dolor sit amet, consectetur adipisici elit
gnu blu bar=3
'''
matches = re.findall(r'^foo.*?bar=\d+$', data, re.DOTALL|re.MULTILINE)
pprint (matches)
答案 2 :(得分:1)
它与MULTILINE
或DOTALL
无关,它是非贪婪的运算符
只影响比赛的结束,而不是开始。
为了满足您的愿望,请在您的模式前添加.*
。
>>> re.findall(r'.*(foo.*?bar=1)', s, re.DOTALL)
['foo lorem ipsum \\pope\n24 dolor sit amet, consectetur adipisici elit\nExcepteur sint obcaecat cupiditat non \ngnu blu bar=1']
>>> re.findall(r'.*(foo.*?bar=2)', s, re.DOTALL)
['foo lorem ipsum @>@!@ consectetur adipisici elit\ngnu blu bar=2']
>>> re.findall(r'.*(foo.*?bar=3)', s, re.DOTALL)
['foo lorem ipsum\n23 dolor sit amet, consectetur adipisici elit\ngnu blu bar=3']