PCRE正则表达式出现问题

时间:2011-07-20 14:26:36

标签: php regex pcre

我正在尝试创建一个可以匹配的正则表达式:

argument ::= define_scope [';' define_scope]*
define_scope ::= (['local'] | 'global') define_var
define_var ::= variable_name expression
variable_name ::= Name

所以,像local varName something;;world foo bar;;local foobar bar 我试过了:

((^|;;)?(local|world) (.+?) (.+?))+

但如果我在上一个例子中使用它,我会得到这些匹配:

local varName s
;;world foo b
;;local foobar b

所以它只需要每场比赛最后一个单词的第一个字母 如果我从最后一个组中删除延迟匹配,则仅匹配:

local varName something;;world foo bar;;local foobar bar

所以最后一组是something;;world foo bar;;local foobar bar

要解决这个问题的一些想法?

3 个答案:

答案 0 :(得分:2)

这不是常规语法,并且无法使用正则表达式解析生成的句子/单词(cs speak)。它是一个无上下文语法,你需要一个利用递归下降(LL-parser)的解析器。

答案 1 :(得分:1)

正则表达式并不是你工具箱中的全部工具,它们在这里是不够的,但是这个可以通过告诉它匹配到(但不是包括)分号,并删除非贪婪的?

/(^|;;)((local|world) (.+?) ([^;]+))/

您的问题是.匹配任何字符。在第一场比赛中,贪婪地匹配.正在吃掉其余的字符串,而非贪婪地对第一个字符感到满意。解决方案是告诉它贪婪地匹配除了半冒号以外的所有内容[^;]+。理想情况下,您应将此限制为您实际希望在其中显示的字符列表,而不是如此自由地使用.

答案 2 :(得分:1)

这是我需要的正则表达式:

((?:(local|world) )?(.*?)(?: (.+?))(?:(?<!;);(?!;)|$))+?

这个可以解析任何有问题的东西;;没有匹配

非常感谢所有人。