【问题标题】:Positive lookahead not working as expected积极的前瞻未按预期工作
【发布时间】:2015-07-11 14:53:36
【问题描述】:

我有以下正则表达式,具有积极的前瞻性:

/black(?=hand)[ s]/

我希望它匹配 blackhandsblackhand。但是,它不匹配任何东西。我正在测试Regex101

我做错了什么?

【问题讨论】:

  • 你真的要匹配“blackhand”后面的空格,还是要确保后面没有除“s”以外的其他字母?如果要匹配“s”或单词的结尾,可以使用(?:s|\b) 而不是[ s],其中\b 匹配单词边界(单词的开头或结尾)。然后它将匹配“blackhand”,当它位于字符串的末尾(后跟空)、句尾(后跟句号)、行尾(后跟换行符)、在子句结尾(后跟逗号),或后跟任何其他标点符号。
  • 断言只是查看字符的某个方向,它们不会移动当前匹配位置。因此,如果您期待hello,然后尝试匹配goodbye,它永远不会匹配。 Fwiw /blackhands?/ 就是你要找的。​​span>
  • 谢谢你们俩;)你们清除了好东西

标签: regex regex-lookarounds


【解决方案1】:

Lookahead 不消耗正在搜索的字符串。这意味着[ s] 正在尝试匹配紧跟在black 之后的空格或s。但是,您的前瞻表明 hand 必须跟随 black,因此正则表达式永远无法匹配任何内容。

要在使用前瞻时匹配 blackhandsblackhand ,请在前瞻内移动 [ s]black(?=hand[ s])。或者,根本不要使用前瞻:blackhand[ s]

【讨论】:

    【解决方案2】:

    您的正则表达式不匹配blackhandsblackhands,因为它试图在文本black 之后匹配空格或字母s(字符类[ s]),并且还向前看hand 之后black.

    要匹配两个输入,您将需要这个前瞻:

    /black(?=hands?)/
    

    或者只是不使用任何前瞻并使用:

    /blackhands?/
    

    Good reference on lookarounds

    【讨论】:

      【解决方案3】:

      简而言之,你应该使用

      /\bblackhands?\b/
      

      现在,您的正则表达式对于这项任务来说有点太复杂了。它由

      • black - 匹配 black 字面意思
      • (?=hand) - 要求 hand 出现在black 之后的正向前瞻 - 但不消耗字符,引擎保持在字符串中的相同位置!
      • [ s] - 匹配空格或 s 的字符类 - 必须紧跟在 black 之后

      因此,您将永远无法获得匹配项,因为空格或s 不会出现在hand 的第一个位置(它是h)。

      这是how lookarounds work

      不同之处在于lookaround实际上匹配字符,但随后放弃匹配,只返回结果:匹配或不匹配。这就是为什么它们被称为“断言”。它们不消耗字符串中的字符,而只是断言匹配是否可能。

      在你的情况下,没有必要。 只需使用\b - 一个word boundary - 来匹配整个单词blackhandblackhands

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2020-05-11
        • 2018-06-30
        • 2012-02-20
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多