正向后顾与非捕获组:不同行为

5 投票
2 回答
2072 浏览
提问于 2025-04-17 14:43

我在代码中使用了Python的正则表达式(re模块),发现了在这些情况下的行为不太一样:

re.findall(r'\s*(?:[a-z]\))?[^.)]+', 'a) xyz. b) abc.') # non-capturing group
# results in ['a) xyz', ' b) abc']

re.findall(r'\s*(?<=[a-z]\))?[^.)]+', 'a) xyz. b) abc.') # lookbehind
# results in ['a', ' xyz', ' b', ' abc']

我想要得到的结果就是 ['xyz', 'abc']。为什么这些例子的表现会不同,我该怎么才能得到想要的结果呢?

2 个回答

0

你需要的正则表达式是:

re.findall(r'(?<=[a-z]\) )[^) .]+', 'a) xyz. b) abc.')

我觉得Anirudha目前的答案很好地解释了你使用正向前瞻和非捕获的区别。不过,建议你去掉正向前瞻后面的?,实际上会得到[' xyz', ' abc'](注意这里面包含了空格)。

这是因为正向前瞻没有匹配到空格字符,而且在主要的匹配字符类别中也没有包含空格

5

第二种情况中,ab被包含的原因是因为(?<=[a-z]\)会先找到a)。由于这种查找方式不会消耗任何字符,所以你又回到了字符串的开头。现在[^.)]+就匹配到了a

接下来你到了)的位置。因为你把(?<=[a-z]\)设为可选,所以[^.)]+就匹配到了xyz

这个过程在b) abc中也是一样的。

如果把第二种情况中的?去掉,你就会得到预期的结果,也就是['xyz', 'abc']

撰写回答