所有正则表达式都停止了吗?

时间:2009-08-06 20:28:01

标签: regex halting-problem

是否有任何正则表达式,对于某些输入字符串,将永远搜索匹配?

8 个答案:

答案 0 :(得分:31)

对于有限输入,没有正式的正则表达式不会停止。

任何正式的正则表达式都可以转化为确定性有限自动机。 DFA一次读取输入的一个字符,并且在输入结束时,您处于接受状态或处于非接受状态。如果状态正在接受,则输入与正则表达式匹配。否则,它没有。

现在,大多数“正则表达式”库都支持非正则表达式的东西,例如反向引用。只要您远离这些功能并且输入有限,就可以保证停止。如果你不......根据你使用的具体内容,你可能无法保证停止。例如,Perl允许插入任意代码,并且不保证任意的图灵机等效代码停止。

现在,如果输入是无限的,那么可以找到永远不会停止的普通正则表达式。例如,“.*”。

答案 1 :(得分:7)

正式正则表达式实际上是一种描述用于解析字符串的确定性有限自动机的方法。如果DFA在输入结束时处于接受状态,则正则表达式“匹配”。由于DFA按顺序读取其输入,因此当它到达输入的末尾时总是停止,并且是否存在匹配仅仅是检查它停止的DFA的状态。

子串匹配实际上是相同的,除了不是在字符串的一个通读结束时被强制暂停,而是在读取每个可能的子字符串之后强制停止DFA - 仍然是有限的情况。 (是的,大多数正则表达式引擎以更优化的方式实现这一点,而不仅仅是在DFA中抛出每个可能的子字符串 - 但从概念上讲,限制仍然存在)。

因此,DFA不会停止的唯一可能情况是输入是无限的,这通常被认为超出了暂停问题的范围。

答案 2 :(得分:2)

我想,找不到不停止的正则表达式是不可能的。

输入的大小是有限的。正则表达式的任何匹配子组的最大大小最大为输入大小。

除非使用的算法非常愚蠢(多次重复使用),否则匹配的子组的数量也是有限的。

所以,它会停止。

答案 3 :(得分:1)

在你所描述的意义上,你可以使用一些非常低效的正则表达式来占用大量资源并最终杀死正则表达式引擎,这与停止不同。

我认为暂停并不适用于这里,正如这篇文章的其他评论者如此敏锐地指出的那样。 http://en.wikipedia.org/wiki/Halting_problem

答案 4 :(得分:1)

根据this question,每个正则表达式都会停止。

答案 5 :(得分:0)

我无法想象一个永远被解析的输入字符串,尽管永远解析一个无限长的字符串。鉴于正则表达式可以描述常规语言,这可能是无限的单词集,那么正则表达式可以描述无限单词的语言,包括无限长度的单词。但是,没有输入字符串可以无限长,因此在某些时候它必须停止。

例如,如果语言中接受了* b,并且你有一个无限长的'a'字符串,那么是的,正则表达式永远不会停止。但实际上,这是不可能的。

答案 6 :(得分:0)

正则表达式可以由有限状态机表示。每次收到原子输入时,都会导致任何定义明确的FSM转换为已知状态。

例外情况是当您有无限输入时,但这不适用于暂停问题,因为它处理有限输入。当您拥有有限状态机和有限输入时,始终可以确定您的机器是否会停止。

http://en.wikipedia.org/wiki/Finite_state_machine

答案 7 :(得分:0)

对于Daniel的回答,

+1:所有有限输入都会导致真正的正则表达式(即没有反向引用或其他非正则表达式功能)停止,而正则表达式相当于DFA。

奖励:正则表达式匹配可以简单快速 (但在Java,Perl,PHP,Python,Ruby等方面都很慢)。

http://swtch.com/~rsc/regexp/regexp1.html

请注意,文章顶部的两个图表在y轴上有不同的比例:一个是秒,另一个是微秒