为什么这个正则表达式前瞻不起作用?

时间:2012-04-20 20:18:32

标签: regex iis url-rewriting negative-lookahead regex-lookarounds

我正在设计一个在一些IIS Url重写中使用的正则表达式。目的是捕获以下网址:

  1. 不仅仅是根目录中的文件(通过包含句点标识)和
  2. 不包含查询字符串,
  3. 不属于特定的子目录集,特别是“帐户”和“公开”
  4. 我目前的正则表达式如下:

    ^(?!(Account)|(Public))([^./]+)(/[^?]*)?$
    

    RegexPal与测试集一起使用:

    file.aspx
    Account/otherfile.aspx
    Public/otherfile.aspx
    otherfolder1/otherfile.aspx?stuff=otherstuff
    otherfolder2/otherfolder/otherfile.aspx
    otherfolder3/
    otherfolder4
    

    我的正则表达式正确地忽略了前两种情况,但它仍然匹配第三种情况。前瞻有什么问题?

4 个答案:

答案 0 :(得分:3)

我无法抗拒试图想出一些可以在RegExPal中工作的东西(没有成功 - 编辑:刚刚验证过,这确实在RegExPal中有用)但是我想我会把它扔掉作为另一种方式来做你需要的东西,这可能会更容易理解:

^(?!Account|Public|[a-zA-Z_0-9]+\.)[a-zA-Z_0-9/.]+$

说明:

^                   # start
(?!                 # open a negative lookahead
Account|Public|     # ignore both Account and Public
[a-zA-Z_0-9]+\.     # ignore files in root (i.e., letters/numbers, followed by period)
)                   # close negative lookahead
[a-zA-Z_0-9/.]+     # now match anything with letters/numbers, periods and slashes, but no '?' (ignores URLs with query string)
$                   # end

答案 1 :(得分:1)

正如sln报道的那样,RegexPal中这些测试的问题在于,运行多行测试可以将多行组合在一起,以创建单个匹配,否则不会。

正则表达式适用于其旨在实现的目的。这实际上是矫枉过正的。对于IIS重写和重定向,如果您使用的是IIS URL Rewrite Module,则可以选择指定它将接受或不接受匹配的条件。其中一些选项包括:

  • 项目不是物理文件
  • 项目不是物理目录
  • 项目确实(或不匹配)辅助模式

这些将比负面前瞻更完全地达到预期的效果。

答案 2 :(得分:1)

RegexPal很困惑,但真正的问题是正则表达式设计不正确。

在使用多线模式和锚点^$时,不确定您要做什么 在正则表达式中,除非你专门设计,否则必须小心 溢出锚。这适用于贪婪/非贪婪量词 当将负面的先行条件投入到混合中时,它变得更糟。

在这种情况下,它导致RegexPal在^之前消失并显然回溯 没有重新评估^。这可能不是JavaScript问题。

在您的消费类中添加非换行符可以解决所有问题。必须是
添加到两个班级。

^(?!Account|Public)[^./\n]+(?:/[^?\n]*)?$

答案 3 :(得分:0)

也许您想使用^(?!Account|Public)([^\.\/]+\/[^\?]*)$正则表达式。

看看这里:http://ideone.com/q3lAv

然后正确的RegExPal模式将是^(?!Account|Public)([^\.\/]+\/[^\?\n]*)$


<强> [UPDATE]

文件名不必在其名称中包含点.,另一方面,文件夹/目录名可能在其名称中包含点.,但如果您想要积极匹配,在第7行,那么你应该使用模式^(?!Account|Public)([^\.\/]+(?:\/[^\?]*|[^\.\?]*))$,它也应该作为RegExPal模式。

看看这里:http://ideone.com/VcmEP