正则表达式命名组(如果存在)

时间:2018-10-04 07:10:59

标签: python regex grouping named

早上好

我有一个字符串,我需要解析并打印两个命名组的内容,因为它们可能不存在。

字符串看起来像这样(基本上是/ proc / pid / cmdline的内容):

"""
<some chars with letters / numbers / space / punctuation> /CLASS_NAME:myapp.server.starter.StarterHome /PARAM_XX:value_XX /PARAM_XX:value_XX /CONFIG_FILE:myapp.server.config.myconfig.txt /PARAM_XX:value_XX /PARAM_XX:value_XX /PARAM_XX:value_XX <some chars with letters / numbers / space / punctuation>
"""

我的进程具有几乎相同的模式,即:

/CLASS_NAME:myapp.server.starter.StarterHome始终存在,但是 /CONFIG_FILE:myapp.server.config.myconfig.txt并不总是存在。

我正在将Python2与re模块一起使用以捕获值。到目前为止,我的模式看起来像这样,我能够捕捉到我想要的与/CLASS_NAME

相对应的值
re.compile('CLASS_NAME:\w+\W\w+\W\w+\W(?P<class>\w+)')

由于是否存在/CONFIG_FILE,我在myregexp中添加了以下内容:

re.compile(r"""CLASS_NAME:\w+\W\w+\W\w+\W(?P<class>\w+).*?
               (CONFIG_FILE:\w+\W\w+\W\w+\W(?P<cnf>\w+.txt))?
            """, re.X)

我的理解是,我的rexexp的第二部分是可选的,因为整个部分都在括号后跟?之间。

不幸的是,我的假设是错误的,因为它无法抓住

我也尝试过删除第一个?,但没有帮助。

我通过PYTHEX进行了几次尝试,以了解我的正则表达式,但是找不到解决方案。

有人可以建议解决我的案件吗?

1 个答案:

答案 0 :(得分:2)

您可以将整个可选部分包装在一个可选的非捕获组中,并强制CONFIG_FILE的捕获组:

re.compile(r"""CLASS_NAME:(?:\w+\W+){3}(?P<class>\w+)(?:.*?
               (CONFIG_FILE:(?:\w+\W+){3}(?P<cnf>\w+\.txt)))?
        """, re.X)

如果有换行符,请使用re.X | re.S修饰符选项。请注意,\w+\W\w+\W\w+\W最好写成(?:\w+\W+){3}

请参见regex demo

主要区别是(?:.*?(CONFIG_FILE:(?:\w+\W+){3}(?P<cnf>\w+\.txt)))?部分:

  • (?:-可选(因为后面有贪婪的?量词)非捕获组匹配的开始
    • .*?-任意0个以上的字符,尽可能少
    • (CONFIG_FILE:(?:\w+\W+){3}(?P<cnf>\w+\.txt))-匹配项
      • CONFIG_FILE:-文字子字符串
      • (?:\w+\W+){3}-三个序列,分别是1个以上的字符字符和1个以上的非字符字符
      • (?P<cnf>\w+\.txt)-组cnf:1个以上的字符,一个点(请注意应转义),然后是txt
  • )?-可选的非捕获组的结尾(将尝试一次)