How do I use grep to perform a search which, when a match is found, will print the file name as well as the first n characters in that file? Note that n
is a parameter that can be specified and it is irrelevant whether the first n characters actually contains the matching string.
如何使用grep执行搜索,当找到匹配项时,将打印文件名以及该文件中的前n个字符?请注意,n是可以指定的参数,前n个字符实际上是否包含匹配的字符串无关紧要。
4 个解决方案
#1
5
grep -l pattern *.txt |
while read line; do
echo -n "$line: ";
head -c $n "$line";
echo;
done
Change -c
to -n
if you want to see the first n
lines instead of bytes.
如果要查看前n行而不是字节,请将-c更改为-n。
#2
4
You need to pipe the output of grep to sed to accomplish what you want. Here is an example:
您需要将grep的输出传递给sed以实现您想要的效果。这是一个例子:
grep mypattern *.txt | sed 's/^\([^:]*:.......\).*/\1/'
The number of dots is the number of characters you want to print. Many versions of sed often provide an option, like -r (GNU/Linux) and -E (FreeBSD), that allows you to use modern-style regular expressions. This makes it possible to specify numerically the number of characters you want to print.
点数是您要打印的字符数。许多版本的sed经常提供一个选项,比如-r(GNU / Linux)和-E(FreeBSD),它允许你使用现代风格的正则表达式。这样就可以在数字上指定要打印的字符数。
N=7
grep mypattern *.txt /dev/null | sed -r "s/^([^:]*:.{$N}).*/\1/"
Note that this solution is a lot more efficient that others propsoed, which invoke multiple processes.
请注意,此解决方案比其他人提供的解决方案更有效,它可以调用多个进程。
#3
3
There are few tools that print 'n characters' rather than 'n lines'. Are you sure you really want characters and not lines? The whole thing can perhaps be best done in Perl. As specified (using grep
), we can do:
很少有工具可以打印'n个字符'而不是'n行'。你确定你真的想要角色而不是线条吗?整个事情也许最好用Perl完成。如指定(使用grep),我们可以:
pattern="$1"
shift
n="$2"
shift
grep -l "$pattern" "$@" |
while read file
do
echo "$file:" $(dd if="$file" count=${n}c)
done
The quotes around $file
preserve multiple spaces in file names correctly. We can debate the command line usage, currently (assuming the command name is 'ngrep
'):
$ file周围的引号正确保存文件名中的多个空格。我们现在可以讨论命令行用法(假设命令名称是'ngrep'):
ngrep pattern n [file ...]
I note that @litb used 'head -c $n
'; that's neater than the dd
command I used. There might be some systems without head
(but they'd pretty archaic). I note that the POSIX version of head
only supports -n
and the number of lines; the -c
option is probably a GNU extension.
我注意到@litb使用'head -c $ n';这比我使用的dd命令更整洁。可能有一些系统没有头(但它们相当古老)。我注意到POSIX版本的头只支持-n和行数; -c选项可能是GNU扩展。
#4
0
Two thoughts here:
这里有两个想法:
1) If efficiency was not a concern (like that would ever happen), you could check $status [csh] after running grep on each file. E.g.: (For N characters = 25.)
1)如果效率不是问题(就像那样会发生),你可以在每个文件上运行grep后检查$ status [csh]。例如:(对于N个字符= 25)
foreach FILE ( file1 file2 ... fileN )
grep targetToMatch ${FILE} > /dev/null
if ( $status == 0 ) then
echo -n "${FILE}: "
head -c25 ${FILE}
endif
end
2) GNU [FSF] head contains a --verbose [-v] switch. It also offers --null, to accomodate filenames with spaces. And there's '--', to handle filenames like "-c". So you could do:
2)GNU [FSF]头包含--verbose [-v]开关。它还提供--null,以容纳带空格的文件名。还有' - ',用来处理像“-c”这样的文件名。所以你可以这样做:
grep --null -l targetToMatch -- file1 file2 ... fileN |
xargs --null head -v -c25 --
#1
5
grep -l pattern *.txt |
while read line; do
echo -n "$line: ";
head -c $n "$line";
echo;
done
Change -c
to -n
if you want to see the first n
lines instead of bytes.
如果要查看前n行而不是字节,请将-c更改为-n。
#2
4
You need to pipe the output of grep to sed to accomplish what you want. Here is an example:
您需要将grep的输出传递给sed以实现您想要的效果。这是一个例子:
grep mypattern *.txt | sed 's/^\([^:]*:.......\).*/\1/'
The number of dots is the number of characters you want to print. Many versions of sed often provide an option, like -r (GNU/Linux) and -E (FreeBSD), that allows you to use modern-style regular expressions. This makes it possible to specify numerically the number of characters you want to print.
点数是您要打印的字符数。许多版本的sed经常提供一个选项,比如-r(GNU / Linux)和-E(FreeBSD),它允许你使用现代风格的正则表达式。这样就可以在数字上指定要打印的字符数。
N=7
grep mypattern *.txt /dev/null | sed -r "s/^([^:]*:.{$N}).*/\1/"
Note that this solution is a lot more efficient that others propsoed, which invoke multiple processes.
请注意,此解决方案比其他人提供的解决方案更有效,它可以调用多个进程。
#3
3
There are few tools that print 'n characters' rather than 'n lines'. Are you sure you really want characters and not lines? The whole thing can perhaps be best done in Perl. As specified (using grep
), we can do:
很少有工具可以打印'n个字符'而不是'n行'。你确定你真的想要角色而不是线条吗?整个事情也许最好用Perl完成。如指定(使用grep),我们可以:
pattern="$1"
shift
n="$2"
shift
grep -l "$pattern" "$@" |
while read file
do
echo "$file:" $(dd if="$file" count=${n}c)
done
The quotes around $file
preserve multiple spaces in file names correctly. We can debate the command line usage, currently (assuming the command name is 'ngrep
'):
$ file周围的引号正确保存文件名中的多个空格。我们现在可以讨论命令行用法(假设命令名称是'ngrep'):
ngrep pattern n [file ...]
I note that @litb used 'head -c $n
'; that's neater than the dd
command I used. There might be some systems without head
(but they'd pretty archaic). I note that the POSIX version of head
only supports -n
and the number of lines; the -c
option is probably a GNU extension.
我注意到@litb使用'head -c $ n';这比我使用的dd命令更整洁。可能有一些系统没有头(但它们相当古老)。我注意到POSIX版本的头只支持-n和行数; -c选项可能是GNU扩展。
#4
0
Two thoughts here:
这里有两个想法:
1) If efficiency was not a concern (like that would ever happen), you could check $status [csh] after running grep on each file. E.g.: (For N characters = 25.)
1)如果效率不是问题(就像那样会发生),你可以在每个文件上运行grep后检查$ status [csh]。例如:(对于N个字符= 25)
foreach FILE ( file1 file2 ... fileN )
grep targetToMatch ${FILE} > /dev/null
if ( $status == 0 ) then
echo -n "${FILE}: "
head -c25 ${FILE}
endif
end
2) GNU [FSF] head contains a --verbose [-v] switch. It also offers --null, to accomodate filenames with spaces. And there's '--', to handle filenames like "-c". So you could do:
2)GNU [FSF]头包含--verbose [-v]开关。它还提供--null,以容纳带空格的文件名。还有' - ',用来处理像“-c”这样的文件名。所以你可以这样做:
grep --null -l targetToMatch -- file1 file2 ... fileN |
xargs --null head -v -c25 --