【问题标题】:Regex capture group flows into second match set正则表达式捕获组流入第二个匹配集
【发布时间】:2012-04-16 13:41:20
【问题描述】:

我正在尝试在同一个正则表达式中匹配多个输入以捕获后面的数字。
如果输入与第一组不匹配,那么我会遇到问题,因为所有先前的捕获组仍然被捕获,尽管它与它们的组不匹配。我相信我需要使用lookaround 断言,但我不熟悉这些。

样本输入:

wordA 123456
wordA: 123456
wordA : 123456
wordA R123465
wordA: R123456
wordA : R123456
wordB R123465

WordA 具有可选的: 和R。到目前为止,我有这个:/(?:wordA :?R?(\d+)|wordB R(\d+))/i.
使用最后一个示例输入提供了以下结果:

array
  0 => string 'wordB R123456' (length=13)
  1 => string '' (length=0)
  2 => string '123456' (length=6)

想要的结果是:

array
  0 => string 'wordB R123465' (length=13)
  1 => string '123456' (length=6)

任何想法如何解决?

【问题讨论】:

    标签: php regex preg-match


    【解决方案1】:

    问题是你的轮换

    /(?:wordA :?R?(\d+)|wordB R(\d+))/i
                  ^^^^^        ^^^^^
                 Group 1       Group 2
    

    因此,如果您的正则表达式与第二个备选方案匹配,则结果将在第 2 组 (array[2]) 中,而第一个组将为空。

    改成这个

    (?:wordA :?R?|wordB R)(\d+)
    

    看here on Regexr

    那么你的号码将永远在第一组(因为只有一个)

    【讨论】:

    • 谢谢。我知道这是因为有 2 个组,但我想如果第一部分不匹配,那么其余部分将被忽略。这是一个错误的假设。
    【解决方案2】:

    您正在定义两个捕获组,因此您将得到两个。正则表达式实现并不关心一次是否只有其中一个可以匹配。您可以将表达式重写为

    /(?:wordA :?R?|wordB R)(\d+)/i
    

    避免定义两个捕获组。请注意,:?R? 不足以将您的测试用例与_:_ 或:_ 匹配。 要获得这些,您可以使用

    /(?:wordA ?:? R?|wordB R)(\d+)/i
    

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 1970-01-01
      • 2014-06-26
      • 1970-01-01
      • 1970-01-01
      • 2015-02-03
      • 1970-01-01
      • 1970-01-01
      相关资源
      最近更新 更多