考虑一下vim中的两个不同的高亮匹配
模式1。
syn match match1 / \ $ [^ $] + \ $ /
匹配$foo$
,$bar$
,$123$
模式2。
syn匹配match2 /(\ w + \ |(\ $ [^ \ $] + \ $)\ @ =)+ __ /
我希望它与foo$bar$__
匹配,但不是$bar$
问题是Pattern1将与Pattern2冲突。
我正在尝试使用Positive Lookahead绕过Pattern2中的Pattern1,
但是前缀__
(双下划线)会破坏正向前瞻的行为。
我该如何解决这个问题?或者我做错了什么!?
更新
抱歉说不好。
模式1匹配由两个美元符号包围的任何字符串
syn match match1 /\$[^$ ]\+\$/
-> $foo$, $bar$
模式2匹配任何带有双下划线的字符串结尾但匹配仍然匹配,但排除任何匹配为Pattern1的字符串。
syn match match2 /\(\w\+\|\(\$[^\$]\+\$\)\@=\)\+__/
-> hello__, world__
所以问题是当我添加任何与模式1相关的字符串
时hello$foo$__
在这种情况下。我想问你好和__匹配模式1(连续)
但也让$ foo $与模式2匹配。
答案 0 :(得分:1)
我认为你不明白前瞻是什么。看起来你要做的就是匹配一个字符串,但跳过它的一部分:
foo$bar$___
^^^~~~~~^^^
...标记为^
的部分形成匹配(不连续),标记为~
的部分将被跳过。
正则表达式无法做到这一点。正则表达式总是匹配连续的字符串。
前瞻是什么让它“向前看”:它像往常一样匹配子正则表达式,但不会移动字符串中的当前位置。根据您放在前瞻的位置,这可以让您检查匹配结束后的文本,或者确保同时使用两个正则表达式匹配相同的字符串(尽管后者也可以在vim中使用\&
完成)。
示例:
\%(foo\)\@=bar
这永远不会匹配。它要求接下来的三个字符同时为foo
和bar
,这是不可能的。
我认为你要找的是重叠的比赛。 Vim直接支持这个:
syn match match1 /\$[^$ ]\+\$/
syn match match2 /\%(\w\|\$[^$ ]\+\$\)\+__/ contains=match1
我们在此处说match2
的匹配项可以包含match1
的匹配项。这为您提供了所需的突出显示。