具有重复组名的正则表达式

regex with repeated group names

我正在尝试制作一个正则表达式,其中我有一些重复的组名,例如,在下面的示例中,我想找到 phA 和 [=14 的值=] 这样,如果我在 pattern 中替换它们,我将检索 string。我使用 regex 执行此操作,因为 Python 的默认 re 库不允许重复名称。

pattern = '(?P<ph>.*?) __ (?P<A>.*?) __ (?P<B>.*?) __ \( (?P<ph>.*?) \-> (?P<A>.*?) = (?P<B>.*?) \) \)'
string = 'y = N __ ( A ` y ) __ ( A ` N ) __ ( y = N -> ( A ` y ) = ( A ` N ) ) )'
match = regex.fullmatch(pattern, string)
for k, v in match.groupdict().items():
    print(f'{k}: {v}')

然后我检索了预期的输出:

ph: y = N
A: ( A ` y )
B: ( A ` N )

我担心的是这个库似乎有一些问题,或者我没有正确使用它。例如,如果我将 string 替换为: string = 'BLABLA __ ( A ` y ) __ ( A ` N ) __ ( y = N -> ( A ` y ) = ( A ` N ) ) )'

然后上面的代码为 phAB 提供完全相同的值,忽略 string 开头的 BLABLA 前缀,并且 match 应该是 None 因为没有解决方案。

有什么想法吗?

注意:更准确地说,在我的问题中,我有一对 patterns/strings (p_0, s_0) ... (p_n, s_n),我必须在这些对中找到一个有效的匹配项,所以我将它们与 __ 连接在一起分隔符,但我也很好奇是否有正确的方法来做到这一点。

由于您要确保前三组与相应的后三组相等,因此您需要对前三组使用 backreferences 而不是使用同名捕获再次分组:

^(?P<ph>.*?) __ (?P<A>.*?) __ (?P<B>.*?) __ \( (?P=ph) \-> (?P=A) = (?P=B) \) \)$

regex demo

此处,(?P=ph)(?P=A)(?P=B)named backreferences 匹配捕获到具有相应名称的组中的相同文本。

^$ 锚点在您的代码中不是必需的,因为您使用 regex.fullmatch 方法,但是当您在正则表达式测试器中在线测试您的模式时需要它们。