perl正则表达式负集匹配字符串在负前瞻中

perl regex negative set matching string in negative lookahead

我正在尝试匹配除方括号 ([^\[\]]+) 之外的任何字符集(在方括号内)——除非字符串的最后一部分匹配 -notme

perl -sp -e 'if (/\[[^\[\]]+?(?!-notme)\]$/../^no/)
 { print "#"; s/^yes/$VAR/; }' -- -VAR="CHANGED" /tmp/input

我的输入文件如下所示:

-bash-4.2# cat /tmp/input 
[test-ing]
yes
yes
no
maybe

[test-ing-notme]
yes
yes
no
maybe

但我的输出看起来像:

#[test-ing]
#CHANGED
#CHANGED
#no
maybe

#[test-ing-notme]
#CHANGED
#CHANGED
#no
maybe

我的猜测是否定集匹配我的否定前瞻不应该匹配的东西——因此我尝试对否定集进行惰性匹配,但结果与贪婪匹配一样。

我的期望是输出如下所示:

#[test-ing]
#CHANGED
#CHANGED
#no
maybe

[test-ing-notme]
yes
yes
no
maybe

您应该将模式更改为:/\[[^\[\]]+?(?!-notme)\]$/

/\[[^]]++(?<!-notme)]$/
#      ^ ^-------------- a negative loobehind before the closing bracket
#      '---------------- a possessive quantifier to prevent backtracking

通过这种方式,您可以确保“-notme”不会在字符串中的无用位置进行测试。

如您所见,如果字符 class 位于第一个位置或紧跟在否定插入符之后,则可以不对字符中的右括号进行转义。