我想将一个正则表达式替换全局应用于目录中和目录下的大约40个Javascript文件。我是一个vim用户,但手动执行此操作可能会很乏味且容易出错,所以我想用脚本自动执行它。
我试过sed,但是一次处理多行是很尴尬的,特别是如果模式可能匹配的行数没有限制。
我也试过这个脚本(在一个文件上进行测试):
ex $1 <<EOF
gs/,\(\_\s*[\]})]\)/\1/
EOF
该模式将消除任何Perl / Ruby样式列表中的尾随逗号,因此“[a,b,c,]”将显示为“[a,b,c]”以满足Internet Explorer ,仅在浏览器中,就会在这些列表上窒息。
该模式在vim中运行得非常漂亮,但如果我在ex中运行它,则不会执行任何操作,如上面的脚本所示。
任何人都可以看到我可能缺少的东西吗?
答案 0 :(得分:12)
您要求提供脚本,但您提到您是vim用户。我倾向于在vim内部进行项目范围内的查找和替换,如下所示:
:args **/*.js | argdo %s/,\(\_\s*[\]})]\)/\1/ge | update
这与其他评论者提到的:bufdo
解决方案非常相似,但它会使用你的args列表而不是你的buflist(因此不需要全新的vim会话,也不需要你注意关闭你不想触摸的缓冲区。)
:args **/*.js
- 将您的arglist设置为包含此目录和子目录中的所有.js文件|
- pipe是vim的命令分隔符,让我们在一行上有多个命令:argdo
- 对所有参数运行以下命令。它将“吞下”后续的管道
%
- 表示整个文件的范围:s
- 替换命令,您已经了解:s_flags
,ge
- 全局(尽可能多替换每行)并抑制错误(即“不匹配”)|
- :argdo
“吞下”此管道,因此以下命令每个参数也会运行一次:update
- 与:write
类似,但仅限于缓冲区已修改这个模式显然适用于你想在多个文件上运行的任何vim命令,所以要记住它是一个方便的。例如,我喜欢用它来删除尾随空格(%s/\s\+$//
),设置统一的行尾(set ff=unix
)或文件编码(set filencoding=utf8
)和retab
我的文件。
答案 1 :(得分:5)
1)用vim打开所有文件:
bash$ vim $(find . -name '*.js')
2)对所有文件应用替换命令:
:bufdo %s/,\(\_\s*[\]})]\)/\1/ge
3)保存所有文件并退出:
:wall
:q
我认为你需要重新检查你的搜索模式,看起来不对。我认为您应该\_\s*
取代\_s*
。
修改:您还应该使用/ge
命令的:s...
选项(我已在上面添加了这些选项)。
答案 2 :(得分:3)
您可以通过从命令行传递参数vi
来自动执行ex
和+'command'
的操作,这样就可以将它们用作文本过滤器。
在您的情况下,以下命令应该可以正常工作:
find /path/to/dir -name '*.js' | xargs ex +'%s/,\(\_\s*[\]})]\)/\1/g' +'wq!'
答案 3 :(得分:1)
您可以结合使用find命令和sed
find /path -type f -iname "*.js" -exec sed -i.bak 's/,[ \t]*]/]/' "{}" +;
答案 4 :(得分:0)
如果你在Windows上,Notepad ++允许你在所有打开的文件上运行简单的正则表达式。
搜索,\s*\]
并替换为]
应该适用于您描述的列表类型。