5

这是一个众所周知的任务,描述起来很简单:

给定一个文本文件 foo.txt 和一个排除字符串的黑名单文件,每行一个,生成 foo_filtered.txt,其中仅包含不包含任何排除字符串的 foo.txt 行。

一个常见的应用程序是从构建日志中过滤编译器警告,但忽略不属于您的文件的警告。文件 foo.txt 是警告文件(它本身是从构建日志中过滤出来的),以及一个带有文件名的黑名单文件 exclude_filenames.txt,每行一个。

我知道它是如何在 Perl 或 AWK 等过程语言中完成的,我什至使用 Linux 命令的组合(如 cut、comm 和 sort)来完成它。

但是我觉得我应该和xargs真的很接近,只是看不到最后一步。

我知道如果excluded_filenames.txt 里面只有1 个文件名,那么

grep -v foo.txt `cat excluded_filenames.txt`

会做的。

而且我知道我可以每行获取一个文件名

xargs -L1 -a excluded_filenames.txt

那么如何将这两者组合成一个解决方案,而无需过程语言中的显式循环呢?

寻找简单而优雅的解决方案。

4

1 回答 1

9

您应该使用该-f选项(或者您可以使用fgrep相同的选项):

grep -vf excluded_filenames.txt foo.txt

您也可以使用-Fwhich 更直接地回答您的问题:

grep -vF "`cat excluded_filenames.txt`" foo.txt

man grep

-f FILE, --file=FILE
          Obtain patterns from FILE, one per line.  The empty file contains zero patterns, and therefore matches nothing.

-F, --fixed-strings
          Interpret PATTERN as a list of fixed strings, separated by newlines, any of which is to be matched.
于 2011-10-10T14:19:36.750 回答