首页 > 解决方案 > 除非在引号中找到,否则如何匹配标识符?

问题描述

假设我有以下字符串,并且我想提取所有以大写字母开头的标识符,除非在引号中找到:

Match1
Match2(Match3("NoMatch1 a NoMatch2 blabla"), Match4)
meh<Match5>

在这种情况下,Match1, Match2, Match3, Match4, 和Match5应该被捕获,而NoMatch1NoMatch2应该被忽略,因为它们在带引号的字符串中。

我可以使用 JS 正则表达式得到想要的结果。链接:(?<=^(\[^\"\]|\"\[^\"\]*\")*)(\b\[A-Z\]\w+\b),但是我所有将其转换为有效的 Python 正则表达式的尝试都失败了。到目前为止我遇到的错误消息:

( A lookbehind assertion has to be fixed width
* A quantifier inside a lookbehind makes it non-fixed width
) A lookbehind assertion has to be fixed width
* A quantifier inside a lookbehind makes it non-fixed width

我不知道如何解决这个问题。这完全有可能使用 Python 正则表达式吗?如果是这样,我错过了什么?

注意:我还没有实际的 Python 代码,到目前为止,我一直在https://regex101.com上进行尝试。

标签: pythonregex

解决方案


您可以使用以下模式:

\b[A-Z]\w+(?=(?:[^\"]*\"[^\"]*\")*[^\"]*$)

演示

诀窍是使用正向 Lookahead(它可以具有非固定长度,与 Lookbehind 不同)。因此,我们使用 Lookahead 来检查成对的双引号(因为每个开始引号都有一个结束引号)。只要要匹配的单词后面跟着偶数个双引号(即双引号),我们就知道它本身没有用引号括起来。


推荐阅读