示例:
搜索:
/lastword\s*\n\zs\(\s*\n\)\{6}\ze\s*startword
此搜索搜索以" lastword"结尾的行之间的6个空行。和一行以" startword"
开头我想抓住与此搜索匹配的空行的亚麻布。
有没有办法在vim中执行此操作?
答案 0 :(得分:5)
您可以使用:g
和:number
(或简称为:#
)打印出包含行号的行。
:g/lastword\s*\n\zs\(\s*\n\)\{6}\ze\s*startword/#
要捕获此内容,您必须使用:redir
将输出重定向到其他位置。在下面这种情况下,我们将其重定向到未命名的寄存器(@"
)
:redir @"|execute 'g/pattern/#'|redir END
注意:必须将:execute
与:g
一起使用,否则redir END
将在:g
命令的每个匹配行上执行。
现在它将通过:#
打印出不是我们想要的起始行(我们想要foo
和bar
之间的空行)。我们可以使用带有:#
命令的范围来完成此任务。
:redir @"|execute 'g/foo\_.*bar/+,/bar/-#'|redir END
范围现在为+,/bar/-
,可转换为开始下一行(+
),搜索bar
(/bar/
)然后减去一行({{1 }})。我们可以简化一些,因为我们知道空行的数量应该是6。
-
我们可以通过将内容放入新缓冲区并删除多余的行来进一步实现。
:redir @"|execute 'g/foo\_.*bar/+#6'|redir END
这里有很多内容,但我们的想法是捕获输出,打开一个新缓冲区,粘贴内容,然后清理输出。
另外,awk可能会让这更容易一些。在当前Vim缓冲区上运行以下命令:
:redir @"|exe 'g/pattern/+#6'|redir END|new|pu|%s/\d\+\zs.*//|%le|g/^$/d
如需更多帮助,请参阅:
:%!awk '/lastword\s*$/,/^\s*startword/ { if($0 ~ /^\s*$/) { print NR} }'