查找包含一个字符串但不包含另一个字符串的文件

查找包含一个字符串但不包含另一个字符串的文件

我位于一个包含大量.txt文件的文件夹中,我想找到包含stringA但不包含的所有文件stringB(它们不一定位于同一行)。有谁知道如何做到这一点?

答案1

只要您的文件名不包含空格、制表符、换行符(假设未修改的$IFS)或通配符并且不以 开头-,并且如果您grep支持该-L选项,则可以按如下方式执行操作:

$ cat file1
stringA
stringC
$ cat file2
stringA
stringB
$ grep -L stringB $(grep -l stringA file?)
file1

grep在子 shell 中执行,$()将打印所有包含stringA.该文件列表是主grep命令的输入,它列出了所有不包含stringB.

man grep

  -v, --invert-match
          Invert the sense of matching, to select non-matching lines.  (-v is specified by POSIX.)
  -L, --files-without-match
          Suppress normal output; instead print the name of each input file from which no output would normally have been printed.  The scanning will stop on the first match.
  -l, --files-with-matches
          Suppress normal output; instead print the name of each input file from which output would normally have been printed.  The scanning will stop on the first match.  (-l is specified by POSIX.)

答案2

使用 GNU 工具:

grep -lZ stringA ./*.txt |
  xargs -r0 grep -L stringB

-L-Z-r-0有时是 GNU 扩展,但并不总是在其他一些实现中找到。

答案3

#run loop for each file in the directory
for i in `ls -l | tail -n+2 | awk '{print $NF}'` ; do
   #check if file contains "string B" 
   #if true then filename is not printed
   if [[ `egrep "string B" $i | wc -l` -eq 0 ]] ; then
      #check if file contains "string A"
      #if false then file name is not printed
      if [[ `egrep "string A" $i | wc -l` -gt 0 ]] ; then
         #file name is printed only if "string A" is present and "string B" is absent
         echo $i
      fi
   fi
done

检查伯恩哈德的答案后:

grep -Le "string B" $(grep -le "string A" `ls`)

如果文件名包含空格:

grep -L stringB $(grep -l stringA `ls -l | tail -n+2 | awk '{print $NF}' | sed -e 's/\s/\\ /g'`

相关内容