现在,在尝试详细说明该问题的答案时,我想了解零长度正则表达式的行为/含义。
我经常使用www.regexr.com作为游乐场来测试/调试/理解正则表达式中发生的事情。
因此,我们有一个最平淡的场景:
正则表达式是 a*
输入的字符串是dgwawa
(事实上,这里的字符串是无关紧要的)
为什么这种行为表示此正则表达式将无限匹配,因为它匹配零次出现的前一个字符?
Why can't the result be 6 matches, one for each character position (since at every character, regardless of whether it is an a or not, there is a match, since zero matches is a match)?
How does it get into matching infinitely ? So it does not check/progress a character at a time?
I wonder how/where does it get itself into an infinite loop.
You selected JavaScript regex flavor at regexr.com online regex tester. JavaScript regex engine does not move the index automatically when a pattern that can match an empty string is passed.
That is why when you need to emulate the behavior observed in .NET Regex.Matches
, PHP preg_match_all
, Python re.finditer
, etc. you need to manually advance the index to test each position.
var re = /a*/g;
var str = 'dgwawa';
var m;
while ((m = re.exec(str)) !== null) {
if (m.index === re.lastIndex) { // <- this part
re.lastIndex++; // <- here
} // <- is important
document.body.innerHTML += "'" + m[0] + "'<br/>";
}
如果删除该if
块,则会出现无限循环。
关于这一点,有两件事要提到:
真好 有人告诉我regexr遵循特定的regex风格。我应该更认真地考虑这一点。
请参阅在线沙箱(用于在线测试和发布正则表达式)部分以选择所需的沙箱。
感谢您提供完整的答案和见解!极好的工作。
仅作记录,.NET regex测试只有一个沙箱,与regexr相比,情况更糟。所以我宁愿坚持使用具有最高意识的regexr :)
要测试.NET应用程序,可以使用regexhero.net和regexstorm.net。而且,如果您需要NET的regex101.com之类的功能,请使用一个非常好的免费应用程序Expresso。