真的需要正则表达式的贪婪选项吗?
假设我有以下文本,我喜欢在[Optionx]和[/ Optionx]块中提取文本
[Option1]
Start=1
End=10
[/Option1]
[Option2]
Start=11
End=20
[/Option2]
Run Code Online (Sandbox Code Playgroud)
但是使用Regex Greedy Option,它会给我
Start=1
End=10
[/Option1]
[Option2]
Start=11
End=20
Run Code Online (Sandbox Code Playgroud)
有人喜欢这样吗?如果是的话,你能告诉我吗?
如果我理解正确,问题是"为什么(什么时候)你需要贪婪匹配?"
答案是 - 几乎总是如此.考虑一个匹配任意 - 但相等 - 字符序列的正则表达式,其长度至少为2.正则表达式如下所示:
(.)\1+
Run Code Online (Sandbox Code Playgroud)
(\1是与第一个带括号的表达式匹配相同文本的反向引用).
现在让我们在以下字符串中搜索重复:abbbbbc.我们发现了什么?好吧,如果我们没有贪婪匹配,我们会发现bb.可能不是我们想要的.事实上,在大多数应用程序中,我们都有兴趣找到bs 的整个子字符串bbbbb.
顺便说一下,这是一个现实世界的例子:RLE压缩就像这样,可以使用正则表达式轻松实现.
事实上,如果你检查周围的正则表达式,你会看到很多人使用量词并期望它们表现得很贪婪.相反的情况可能是少数.通常,它没有区别,因为搜索的表达式是在保护子句中(例如,引用的字符串在引号内),但是在上面的例子中,情况并非总是如此.
正则表达式可能匹配文本的多个部分.
例如,考虑表达式(ab)*c+和字符串"abccababccc".字符串的许多部分可以匹配正则表达式:
(abc)cababccc
(abcc)ababccc
abcc(ababccc)
abccab(abccc)
ab(c)cababccc
ab(cc)ababccc
abcabab(c)ccc
....
Run Code Online (Sandbox Code Playgroud)
一些正则表达式实现实际上能够返回整个匹配集,但最常见的是返回单个匹配.
有许多可能的方法来确定"获胜的比赛".最常见的是采用" 最长的最左边的匹配 ",这会导致你观察到的贪婪行为.
这是一个典型的搜索和替换(a la grep),当a+你可能意味着匹配整个aaaa而不仅仅是一个a.
选择"最短的非空最左边"匹配是通常的非贪婪行为.当你有像你的情况一样的分隔符时,它是最有用的.
这一切都取决于你需要什么,有时贪婪是好的,有些时候,就像你展示的情况一样,非贪婪的行为会更有意义.正则表达式的现代实现允许我们同时执行这两个操作,这很好.