解析前后没有特定字符的参数模式

时间:2016-07-22 10:35:21

标签: php regex

练习我创建自己的PHP路由器。此路由器可以接收如下指定的参数:

  

{I:VARIABLENAME}

i代表参数类型(在本例中为整数),variableName代表变量名。

单个路由URI可能如下所示:

  

/家庭/ {I:ID} - {S:傲华尔} / {M:的varName} / {S:一些其它}

我为此目的创建了以下正则表达式模式:

[^{}]*({((?<type>\D):)?(?<name>[a-zA-Z_-ÿ][a-zA-Z0-9_-ÿ]+)})[^{}]*

由于没有2个参数彼此相邻,并且旁边有一个字符,我用这个部分展开了正则表达式:

[^{}]*

这方面的一个例子是我无法做到这样的事情:

  

/家庭/ {I:ID} {S:傲华尔} / {M:的varName} {S:一些其它}

它们之间需要有字符。

我认为这段正则表达式会做,&#34;不要包含零个或多个{}字符。

当我在/home/{i:id}{s:noVar}/{m:varName}/{s:someOther}这样的模式上运行此正则表达式时,它仍会检索所有参数,甚至是彼此相邻的参数。

这怎么可能?我怎样才能使正则表达式只检索彼此不相邻的参数?

1 个答案:

答案 0 :(得分:1)

我建议匹配2个或更多连续的{...}块并忽略这些匹配,并且只处理所有其他{...}(非相邻)块。使用着名的PCRE (*SKIP)(*F) technique

(?:{(?:[a-zA-Z]:)?[a-zA-Z_]\w*}){2,}(*SKIP)(*F)|{(?:(?<type>[a-zA-Z]):)?(?<name>[a-zA-Z_]\w*)}

请参阅regex demo

<强>解释

  • (?:{(?:[a-zA-Z]:)?[a-zA-Z_]\w*}){2,}(*SKIP)(*F) - 正则表达式中第一个替代分支(2)与下面解释的模式(只是没有捕获组)相匹配,连续出现,请参阅{2,}表示匹配一次发生2次或更多次(*SKIP)(*FAIL)动词使正则表达式引擎省略此匹配并继续。
  • | - 或匹配我们需要的内容:
  • { - 开放{
  • (?:(?<type>[a-zA-Z]):)? - 与ASCII字母匹配的可选组(捕获到组&#34;类型&#34;)和:
  • (?<name>[a-zA-Z_]\w*) - Group&#34; name&#34;捕获ASCII字母或_(参见[a-zA-Z_]后跟0 +字符(来自[a-zA-Z0-9_]范围)
  • } - 关闭}