2016-03-30 20 views
4

在vi中,用于线路有没有上下文替换的标准?

aaaj

我运行命令:

.S/A * \ |焦耳/ X /克

的线变为

XJ

,而不是预期

XX

这是VI的错误吗? SED,呆子,和NAWK像预期,例如:

% echo aaaj | awk '{gsub(/a*|j/,"x");print}' 
xx 

另外,如果代替上面的命令我运行命令

.S/J \ | A */X /克

(“j”和“a *”交换),则该行将如预期的那样变成“xx”。

+0

正则表达式有不同的风格,请参阅vi的文档以了解如何在那里实现正则表达式。 –

+2

“查看文档”是几乎任何问题的答案在stackoverflow。显然,如果我能在文档中找到它,我不会问。 – user31264

+1

从理论上讲,它应该替换'a *'和'j',因为DFA对于'a * \ | j'和'j \ | a *'都是相同的。你的问题很好。由于我的回答没有回答原来的问题,我删除了它。 – doptimusprime

回答

3

这里的“问题”是a*子模式,即变更中的第一个分支可以匹配空字符串

当引擎找到aaa,该a*选择分支匹配三个a s和substitute取代所有这些与x。然后,发动机在 s + 1(source code comments)之后试图再次匹配的位置。

请注意,a*总是匹配,“胜利”和j永远不会匹配。这是因为优先顺序的原因,第一个分支总是在Vim正则表达式中获胜。如果替换aaaj jjj它将变为xjx xjxjxj,因为该模式将匹配不匹配的字符之前的每个位置。

正确的方式

当用正则表达式替换,你通常不想匹配不匹配模式字符之间的所有空的位置,因此,合理的解决方案是使用+量词,a\+\|j模式