带正则表达式的无限循环

时间:2012-11-26 10:00:48

标签: regex roundhouse

我们在一个更面向SQL的项目中使用RoundhousE迁移工具。我有一个非常奇怪的错误

某个SQL函数脚本(遗憾的是我无法提供脚本,因为它是我的客户的属性)使得RegEx的Replace方法永远不会返回

正则表达式看起来像这样

(?<KEEP1>^(?:[\s\t])*(?:-{2}).*$)|(?<KEEP1>/{1}\*{1}[\S\s]*?\*{1}/{1})|(?<KEEP1>'{1}(?:[^']|\n[^'])*?'{1})|(?<KEEP1>\s)(?<BATCHSPLITTER>GO)(?<KEEP2>\s)|(?<KEEP1>\s)(?<BATCHSPLITTER>GO)(?<KEEP2>$)

RounhousE中永不返回的代码行

string sql_statement_scrubbed = regex_replace.Replace(sql_to_run, match => evaluate_and_replace_batch_split_items(match, regex_replace));

问题不在委托evaluate_and_replace_batch_split_items中,在实际的regex.Replace方法中,我在一个简单的正则表达式工具中尝试了正则表达式,它也挂了。也许这里的人是RegEx的大师可以看出问题是什么?

编辑:如果我从此评论-- If no previous, don't report revised中移除'(撇号) 它的工作原理,但它不仅必须是脚本中其他文本的组合,因为该行可以自行运行

1 个答案:

答案 0 :(得分:2)

通常情况下,当正则表达式永远匹配时(或者,更有可能发现它不匹配),这是因为灾难性的回溯。你的正则表达式中有一些实例可能容易发生这种情况,具体取决于你的输入是什么样的。我已经拿走你的正则表达并清理了一点,删除了许多不必要的量词和替换。这个正则表达式:

(?<KEEP1>^\s*--.*$)|(?<KEEP1>/\*[\S\s]*?\*/)|(?<KEEP1>'[^']*')|(?<KEEP1>\s)(?<BATCHSPLITTER>GO)(?<KEEP2>\s|$)

将与旧的正则表达式完全相同,但它不那么复杂,应该更稳定。请试一试。

要正确处理字符串('It\'s something else!')中的转义撇号,您需要更改正则表达式:

(?<KEEP1>^\s*--.*$)|(?<KEEP1>/\*[\S\s]*?\*/)|(?<KEEP1>'(?:\\.|[^'\\])*')|(?<KEEP1>\s)(?<BATCHSPLITTER>GO)(?<KEEP2>\s|$)