Python re库命名捕获组过于贪婪 如何正确匹配指定区间内容
问题原因
你的正则写法的核心问题是没有限制匹配的(the|my)是目标Foo之前最后出现的前缀:
- 正则匹配默认从左到右扫描字符串,会优先命中第一个出现的
the或my作为前缀 - 即便你用了非贪婪量词
.+?,也只是在已经匹配到前缀的基础上,尽可能少匹配字符到下一个Foo,因此会把前缀和目标Foo中间的所有内容(包括中间出现的其他the/my)都捕获到bar分组中,就出现了捕获内容超出预期的问题。
解决方法
可以在正则开头加贪婪匹配.*,让引擎先吃掉尽可能多的字符,直到命中最后一个出现的the或my,再捕获后续到Foo之前的内容即可,修改后的正则为:
.*(the|my) (?P<bar>.+?) Foo
如果需要严格避免捕获内容中出现其他the/my,也可以用否定前瞻的写法实现:
(the|my) (?P<bar>(?:(?!\bthe\b|\bmy\b).)+) Foo
Python 实现示例
import re text = """FooFooFoo the FooFoo the Bar Foo FooFooFoo the FooFoo my Bar Foo FooFooFoo the FooFoo the Hello World Foo """ pattern = re.compile(r'.*(the|my) (?P<bar>.+?) Foo') for line in text.splitlines(): match = pattern.search(line) if match: print(match.group('bar'))
运行后输出:
Bar Bar Hello World
内容的提问来源于stack exchange,提问作者mistyped
相关产品推荐
相关产品推荐

