具有特殊表达式的 grep

具有特殊表达式的 grep

.c我的目录中有一些二进制文件和一些扩展文件。

这里的输出使用ls

arrays.c basic0 basic0.c fromfb fromfb.c oute oute.c segmen.c simp simp.c

这里我只想过滤二进制文件,所以我使用

ls |grep -v .c

此命令列出所有文件,然后使用grepI 获取文件,除了那些不以 .c 结尾的文件

我期望的是

basic0
fromfb
oute
simp

但我得到了什么

fromfb
oute
simp

basic0 二进制文件丢失。这有什么问题吗?

答案1

按照man grep

时期 。匹配任何单个字符。

因此grep .c匹配后面跟随的任何字符c

您可能正在寻找grep -v \.c或更好的grep -v '\.c$'

在哪里

  • \.逃逸的特殊含义。
  • c
  • $行尾(当通过管道传输到 ls 时,输出一个文件名)

正如通配符所建议的,您还可以使用grep -vF .c-F标志告诉 grep 使用 arg 作为简单字符串,而不是正则表达式。

答案2

您需要使用“\.”转义点号。尝试使用ls | grep -v "\.c$".执行grep -v .c是指任何不包含该字符的记录C 前面有另一个字符

答案3

男人

man grep告诉我们

时期 。匹配任何单个字符。

这意味着.c匹配任何单个字符后跟C。由于您尚未锚定表达式,因此这会匹配包含任何字符后跟的任何字符串C

让我们测试一下。如果我们不使用该-v标志怎么办?

测试

让我们来看看。首先,我们设置一个测试

~ $ mkdir test
~ $ cd test
~/test $ touch arrays.c
~/test $ touch basic0
~/test $ touch basic0.c
~/test $ touch fromfb
~/test $ touch fromfb.c
~/test $ touch oute
~/test $ touch oute.c
~/test $ touch segmen.c
~/test $ touch simp
~/test $ touch simp.c
~/test $ ls
arrays.c  basic0.c  fromfb.c  oute.c    simp
basic0    fromfb    oute      segmen.c  simp.c

然后我们测试ls | grep .c

~/test $ ls|grep .c
arrays.c
basic0
basic0.c
fromfb.c
oute.c
segmen.c
simp.c

正如您所看到的,不仅预期的 C 源代码匹配,而且二进制文件basic0也匹配。这.与和相匹配C与(毫不奇怪)匹配c

解决方案

您想要匹配 C 源以排除它们。这些文件以。C,所以我们告诉 grep 来匹配这些。

~/test $ ls|grep "\.c$"
arrays.c
basic0.c
fromfb.c
oute.c
segmen.c
simp.c

我们在这里做了两件事。首先,我们转义了点,使其成为文字点而不是“任何单个字符”。但这仍然会匹配一个名为的文件,foo.c.bar该文件可能是也可能不是您的目标。
假设不是,我们还将 c 固定为最后一个字符。现在您正在匹配的字符串结尾带有一个点和一个C

重新申请-v留给读者作为练习。

相关内容