这个问题对于获取Vim中某个模式的计数是有帮助的,但是对我来说存储计数并对结果求和将是有用的,所以我可以回应一个简明的总结.
我正在为一些高中生教授基础HTML课程,我正在使用这个脚本在不离开Vim的情况下快速检查所有页面中所需元素的数量.它工作正常,但是当学生有超过10个.html
文件时,手动添加各个部分会很麻烦.
就像是:
img_sum = :bufdo %s/<img>//gen
Run Code Online (Sandbox Code Playgroud)
会好的.我想我会编写一个ruby脚本来更彻底地检查页面并检查结构,但是现在我很好奇如何在Vim中执行此操作.
该问题可以通过与:substitute
命令中内置的计数器分开来解决
:使用Vim-script变量来保存模式匹配的数量.注册每个匹配并相应地修改特定变量的便捷方法是利用:substitute
命令的表达式特征替换(参见参考资料:help sub-replace-\=
).我们的想法是使用一个替换来计算每次出现时增加一个计数器的表达式,并且不会更改它正在操作的文本.
该技术的第一部分无法直接实现,因为禁止在表达式(包括\=
替换表达式)中使用Ex命令,因此无法使用该:let
命令修改变量. 回答 " gVim查找/替换计数器 "的问题,我提出了一个简单的技巧来克服这个限制,它基于使用单项列表(或包含单个键值对的字典).由于map()
函数转换了列表或字典,因此只能在受约束的表达式上下文中更改项目.要做到这一点,应该调用map()
函数传递一个表达式来评估新值以及包含当前值的列表.
该技术的后半部分是在使用替换命令时如何避免更改文本.为了实现这一点,人们可以使图案通过预先具有零宽度\ze
或通过附加\zs
原子(见
:help /\zs
,:help /\ze
).以这种方式,修改的图案在初始图案出现之前或之后捕获零宽度的串.因此,如果替换文本也为空,则替换不会导致缓冲区内容发生任何变化.要使替换表达式求值为空字符串,可以从该表达式的结果值中提取空子字符串或子列表.
这两个想法在以下命令中付诸实施.
:let n=[0] | bufdo %s/pattern\zs/\=map(n,'v:val+1')[1:]/ge
Run Code Online (Sandbox Code Playgroud)