Grep输出通常是这样的:
after/ftplugin/python.vim:49: setlocal number
我是否可以使用标准的linux实用程序从此结果中提取文件名和行号?寻找一个非常好用的通用解决方案。
我可以考虑使用awk来获取第一个字符串:
输入
echo 'after/ftplugin/python.vim:49: setlocal number' | awk 'print $1'
'after/ftplugin/python.vim:49:'
$
预期
after/ftplugin/python.vim and 49
目标:在Vim中打开
我正在编写一个小函数,将grep输出转换为vim可以理解的东西 - 主要用于学术目的。我知道有像Ack.vim那样的想法做了类似的事情。什么是标准的轻量级工具?
编辑:grep -n "text to find" file.ext |cut -f1 -d:
似乎是这样做的,如果你不介意双解析字符串。但是需要使用Sed!
答案 0 :(得分:2)
如果您使用Bash
,可以这样做:
IFS=: read FILE NUM __ < <(exec grep -Hn "string to find" file)
vim "+$NUM" "$FILE"
或POSIX:
IFS=: read FILE NUM __ <<EOD
$(grep -Hn "string to find" file)
EOD
vim "+$NUM" "$FILE"
样式©konsolebox:)
答案 1 :(得分:2)
这样做:
echo 'after/ftplugin/python.vim:49: setlocal number' | awk -F: '{print $1,"and",$2}'
after/ftplugin/python.vim and 49
但在grep
之前向我们提供数据。可能我们可以减少更多。无需grep
和awk
答案 2 :(得分:1)
这个怎么样?:
echo 'after/ftplugin/python.vim:49: setlocal number' | cut -d: -f1-2 | sed -e 's/:/ and /'
结果:
after/ftplugin/python.vim and 49
答案 3 :(得分:1)
如果通过&#34;反向解析&#34;你的意思是你想从头开始(并且可以安全地假设文件内容不包含冒号),参数扩展使这很容易:
line='after/ftplugin/python.vim:49: setlocal number'
name_and_lineno=${line%:*}
name=${name_and_lineno%:*}
lineno=${name_and_lineno##*:}
全部在进程中(使用shell内置功能),这比使用sed,awk等外部工具要快得多。
要将它们连接在一起,请考虑以下循环:
while read -r line; do
...
done < <(grep ...)
现在,要处理所有可能的文件名(包括冒号的文件名)和所有可能的内容(包括带冒号的字符串),你需要一个带有GNU扩展名的grep:
while IFS='' read -u 4 -r -d '' file \
&& read -u 4 -r -d ':' lineno \
&& read -u 4 -r line; do
vim "+$lineno" "$file"
done 4< <(grep -HnZ -e "string to find" /dev/null file)
其工作原理如下:
grep -Z
(GNU扩展名)使用NUL终止每个文件名而不是:
IFS='' read -r -d ''
读取文件名时的第一个NUL read -r -d ':' lineno
读取直到冒号
-u 4
的所有调用使用read
参数来处理来自FD#4的内容