Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/java/327.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
java问题中的regexp_Java_Regex - Fatal编程技术网

java问题中的regexp

java问题中的regexp,java,regex,Java,Regex,我在测试NLP系统时发现了一些问题。我有一个java正则表达式“(.\\\\\s*)*Dendryt.*”,对于string“v目录表”…..,它只是不停止计算 很明显,这个正则表达式的复杂性非常高,我将尝试重构它。你对我未来的正则表达式开发有什么建议吗 谢谢。通过重复包含重复量词的组,您将遇到。随后的组合爆炸(给定足够的输入)将导致(tada!)堆栈溢出 简化,您的正则表达式尝试 (.*.\s*)匹配任何连续字符,包括点和空格,后跟一个点,后跟零个或多个空格,然后 (…)*重复此操作任意次数

我在测试NLP系统时发现了一些问题。我有一个java正则表达式
“(.\\\\\s*)*Dendryt.*”
,对于string
“v目录表”…..
,它只是不停止计算

很明显,这个正则表达式的复杂性非常高,我将尝试重构它。你对我未来的正则表达式开发有什么建议吗

谢谢。

通过重复包含重复量词的组,您将遇到。随后的组合爆炸(给定足够的输入)将导致(tada!)堆栈溢出

简化,您的正则表达式尝试

(.*.\s*)
匹配任何连续字符,包括点和空格,后跟一个点,后跟零个或多个空格,然后

(…)*
重复此操作任意次数

Dendryt
只有当它尝试匹配“Dendryt”时

由于此操作失败,引擎将返回,尝试不同的排列。可能性几乎是无穷无尽的

为了说明这一点,下面是RegexBuddy的regex调试器在简化版数据上的屏幕截图:

100万次置换后,引擎停止运行

您的正则表达式会更好(在将其转换为Java字符串时,不要忘记避开反斜杠):

在这种情况下,
*+
,一个所谓的所有格量词,一旦匹配就会拒绝回溯。这样,正则表达式引擎可能会更快地失败,但仍然很糟糕,因为
(.*)
匹配任何东西,甚至点

([^.]*)(\.\s*)*+Dendryt
是安全的,除非您的数据可以在“虚线位”之前包含点。总而言之,请更清楚地说明您的要求,然后可以构建更好的正则表达式。

尝试以下方法:

"[^.]*+(?>\\.\\s*)*+Dendryt.*"
[^.]*+
消耗第一个点之前的所有内容,而
+
生成
*
,因此正则表达式永远不会回溯到该点

(?>\\.\\s*)
是一个:它匹配一个点和任何后续空格,就像它是一个单位一样。如果正则表达式引擎必须回溯到该点,它将直接跳过该点,转到组开始匹配的位置

但它不会回到这一点,因为我把这个组的量词也设为所有格。我想说明原子群的用法,但我可以将
\\s*
设为所有格,或者两者兼而有之

所有格量词和原子组完全禁用回溯,但并不总是可以使用它们。当您必须允许回溯时,将其保持在最小值;不要让量词消耗过多。特别是,正如Tim所说,避免嵌套的量词和可以匹配相同事物的量化子表达式


事实上,避免使用
*
+
是一个很好的练习;它迫使你思考它的机制。如果没有您想要匹配的特定内容,请考虑您不想要匹配的内容,例如我使用
[^.]*
代替正则表达式中的第一个
*

正则表达式的这部分
(?:....*.\s*)*

表示获取尽可能多的具有
文字点,如果是连续线,则在末尾。这是必需的,直到最后找到
Dendryt
literal。一旦找到它,还可以得到该行的剩余部分

使用一个简单的原子群
(?>\uux)

就可以很容易地做到这一点 但是,由于它是原子的,如果在组中使用
*
,它将不会停止
检查是否找到最终的
Dendryt
,因为它不会返回

解决方案是使用惰性量词
*?
。然后原子组将
允许检查最后一个
Dendryt

注意,我不确定您的真正意图是什么,只是使用正则表达式 提供以说明其目前的工作方式,并提供不适用的等效项 导致回溯问题(我看到的是)

解决方案:

(?>.*.\.\s*)*Dendryt.*


非常感谢,非常有帮助!:)
"[^.]*+(?>\\.\\s*)*+Dendryt.*"