在嵌套的substitute()命令中转义会导致7.2中的^ @字符

时间:2013-04-06 03:18:36

标签: regex vim escaping substitution

我有一份文件:

"""I'm a multiline string.
I say 
  "hey, single line string", 
and it says 
  "\they, multiline string,\nI can do multiple lines\ntoo".
and I say, 
  "it's cute that you think you can".

Yeah, I'm kind of a jerk."""

我可以使用嵌套的substitute()对其进行转换:

:%s/"""\(\_.\{-}\)"""/\='"'.substitute(submatch(1),'["\\\n]','\\\0','g').'"'/g

在vim 7.3中,我得到了我想要的东西:

"I'm a multiline string.\
I say \
  \"hey, single line string\", \
and it says \
  \"\\they, multiline string,\\nI can do multiple lines\\ntoo\".\
and I say, \
  \"it's cute that you think you can\".\
\
Yeah, I'm kind of a jerk."

但是,在vim 7.2中,我得到了相同输入和命令的不同结果:

"I'm a multiline string.^@I say ^@  "hey, single line string", ^@and it says ^@ "\they, multiline string,\nI can do multiple lines\ntoo".^@and I say, ^@  "it's cute that you think you can".^@^@Yeah, I'm kind of a jerk." 

(据我所知,^@为零字节)。

为什么我会遇到如此截然不同的行为?我应该如何修改:%s命令以在7.2和7.3中产生相同的效果?

1 个答案:

答案 0 :(得分:1)

我认为您遇到的行为是由修补程序7.3.225修复的错误引起的:

  

“\ n”在替换()里面“:s”未正确处理

Vim 7.2来自2008年,非常过时。应该可以安装最新版本7.3;如果找不到适合您的发行版的软件包(对于Windows,请检查Cream project中的二进制文件,对compile(例如来自Mercurial源)的Linux也不是很困难。

如果您确实需要支持较旧的Vim版本并找到解决方法,则可以实现条件:

if v:version > 703 || v:version == 703 && has('patch225')
    " new implementation
else
    " workaround
endif