Python 正则表达式命名组

Python Regular Expression named groups

我正在尝试构建一个正则表达式来捕获任何数字(整数、浮点数、是否使用科学记数法)。我正在使用组,这样如果我需要更新某些内容,我只更新一行。这是我正在做的事情:

intNumber = r"(?P<Integer>-?(0|[1-9]+[0-9]*))" # Integer
floatNumber = r"(?P<Float>"+intNumber+r"\.[0-9]+)" # Float
sciNumber = r"(?P<Scientific>"+floatNumber+r"(e|E)(-|\+)?[0-9]+)" # Scientific
anyNumber = r"(?P<AnyNumber>"+sciNumber+"|(?P=Integer)|(?P=Float))" # Any number

问题是,虽然每个正则表达式都独立工作,但当我使用或 (|) 将它们全部组合在 anyNumber 中时,它只捕获科学记数法数字而不捕获其余部分。我做错了什么?

编辑: 为了完善我的问题,是否可以有一个动态生成的正则表达式(以简单的单点维护为目标)并且足够灵活以允许我单独使用它的组件,没有像重新定义组和方便的组命名这样的问题?我知道我可能要求太多了..

(?P=Integer) 是一个命名的 backreference 匹配相同的文本(不递归组子模式!)由名为 "Integer" 的捕获组创建。 (?P=Float) 也是如此。这意味着,您需要使用模式本身,而不是反向引用。

此外,如果您计划以这种方式动态构建正则表达式,则不能使用命名反向引用。使用非捕获组,您的模式构建将类似于

import re
intNumber = r"-?(?:0|[1-9]+[0-9]*)" # Integer
floatNumber = intNumber+r"\.[0-9]+" # Float
sciNumber = floatNumber+r"[eE][-+]?[0-9]+" # Scientific
anyNumber = r"{0}|{1}|{2}".format(sciNumber,floatNumber,intNumber) # Any number
print(re.findall(anyNumber, '12 12.34 12.34E-34'))

Python demo

我最后做了以下事情:

intNumber_re = r"(?P<Integer>-?(0|[1-9]+[0-9]*))" # Integer
floatNumber_re = r"(?P<Float>"+intNumber_re+r"\.[0-9]+)" # Float
sciNumber_re = r"(?P<Scientific>"+floatNumber_re+r"[eE][-\+]?[0-9]+)" # Scientific
groupNames_re = r'(\?P<Integer>)|(\?P<Float>)|(\?P<Scientific>)'
anyNumber_re = r"(?P<AnyNumber>{0}|{1}|{2})".format(re.sub(groupNames_re,'?:',sciNumber_re),
               re.sub(groupNames_re,'?:',floatNumber_re),re.sub(groupNames_re,'?:',intNumber_re)) # Any number

实际上,当我使用 re.sub() 函数构建 anyNumber RE 时,我删除了组名(正则表达式在 groupNames_re 中)。它有点难看,但它确实有效,并为我提供了我想要的灵活性。感谢 Wiktor 的输入,我最终使用了一些你的代码:)