跳转到内容

Grep

100% developed
来自维基教科书,开放的书籍,为开放的世界

Grep 是一个 Unix 实用程序,它搜索通过管道传递给它的信息,或当前目录中的文件。一个例子应该有助于澄清事情。

假设我们要搜索一个目录,并想找到所有名称中包含字符串 "hello" 的文件。你可能会在 shell 中发出 'ls' 命令来列出目录的内容,并

$ ls
DumpSite.sh  crontab.txt  nagios-3.0.6  xmpppy  xymon-4.3.0-beta2

并手动查看所有内容,或者你可以使用 'ls' 命令并将 'ls' 的输出管道到 grep

$ ls |grep crontab
crontab.txt

相反,如果你想过滤一个列表,除非某些条目,将其放在参数 -v 中

$ ls |grep -v crontab
DumpSite.sh
nagios-3.0.6
xmpppy
xymon-4.3.0-beta2

'|' 字符是管道表示法,它基本上将 'ls' 命令的输出作为 grep 的输入。你应该会得到一个包含所有名称中包含 "hello" 的文件的列表(可能是空的)。

对于搜索词,grep 可以接受正则表达式,而不是普通字符串。一个简单的例子可能是查找目录中的所有 .txt 或 .jpg 文件

$ ls | grep '.*\(txt\|jpg\)'

这里的正则表达式由 .* 组成,它可以代表文件名中的任何内容,以及 \(txt\|jpg\) ,它产生 txt 或 jpg 作为文件扩展名。

grep 的命令行选项,又称开关

  • -e 模式
  • -i: 忽略大小写。
  • -v: 反转匹配。
  • -c: 只输出匹配行的数量。
  • -l: 只输出匹配的文件。
  • -n: 在每条匹配行之前加上行号。
  • -b: 一个历史上的好奇现象:在每条匹配行之前加上块号。
  • -h: 输出匹配行,但不要在它们前面加上文件名。
  • -s: 抑制关于不存在或不可读文件的错误消息。
  • -x
  • -f 文件:从文件中获取正则表达式。
  • -o: 输出匹配行中匹配的部分。

GNU grep 的命令行选项,又称开关,超越了基本的 grep

  • --help
  • -V, --version
  • --regexp=模式,除了 -e 模式
  • --invert-match,除了 -v
  • --word-regexp,除了 -w
  • --line-regexp,除了 -x
  • -A 数值, --after-context=数值
  • -B 数值, --before-context=数值
  • -C 数值, -数值, --context=数值
  • 等等...

链接

正则表达式

[编辑 | 编辑源代码]

Grep 使用一种特殊的正则表达式版本,不同于 sed 和 Perl。Grep 涵盖了 POSIX 基本正则表达式(另见 正则表达式/Posix 基本正则表达式)。

grep 中可用的正则表达式功能包括 *、.、^、$、[ ]、[^ ]、\( \)、\n、\{i\}、\{i,j\}、\{i,\}。

GNU grep 中可用的正则表达式功能,作为 GNU 扩展,包括 \?、\+、\b、\B、\<、\>、\w、\W、\s、\S。

grep 中带有 -E 开关可用的正则表达式功能包括 ?、+、|、( )、{i}、{i,j}、{i,}。

grep 支持的预定义字符类包括 [:alpha:]、[:blank:]、[:cntrl:]、[:digit:]、[:graph:]、[:lower:]、[:print:]、[:punct:]、[:space:]、[:upper:] 和 [:xdigit:]。

grep 中不可用的正则表达式功能包括 Perl 的 \d、\D、\A 和 \Z。

链接

当从 find 调用 grep 时,让 grep 输出文件的完整路径,然后输出匹配的内容非常有用。为了做到这一点,让 grep 认为它是被多个文件调用的,在 {} 后面加上 /dev/null,就像这样

 find /var/www -exec grep php {} /dev/null \;

grep 使用的例子

  • echo file.txt | grep ".*\(txt\|doc\)"
    • 匹配。"\(" 和 "\)" 创建一个组,而 "\|" 分隔组中的项目。如果至少有一个项目匹配,则该组匹配。
  • echo a456 | grep "[a-zA-Z][0-9][0-9]*"
    • 匹配。 "[" 和 "]" 是字符组的定界符。 "*" 代表 0 个、1 个或任何其他数量的前面内容。
  • echo a456 | grep -i "[A-Z][0-9]\+"
    • 匹配。"\+" 代表前面内容的 1 个或多个出现。与 "*" 不同,"+" 必须以 "\" 开头。"-i" 使搜索不区分大小写。
  • echo file.txt | grep -E ".*(txt|doc)"
    • 匹配。"-E" 代表扩展正则表达式。在扩展正则表达式中,"(" 和 "|" 不需要 "\" 就可以充当特殊字符;它们需要 "\" 才能充当字面量,也就是说,代表它们自身。
  • echo abbc | grep -E "abb?c"
    • 在 -E 开关启用的扩展正则表达式中,问号匹配前面内容的 0 个或 1 个出现。
  • echo abbc | grep "abb\?c"
    • 在 GNU Grep 中,\?(反斜杠后面的问号)匹配前面内容的 0 个或 1 个出现。
  • echo a4c | grep -P "a\dc"
    • 在某些版本的 GNU Grep 中,匹配。"-P" 代表 Perl 正则表达式;正则表达式中的 "\d" 代表一个数字。
  • grep -P "\x22hello\x22" file.txt
    • 在某些版本的 GNU Grep 中,搜索以引号开头、接着是 "hello"、再接着是另一个引号的字符串。利用了 -P,它开启了 Perl 正则表达式。在 Perl 正则表达式中,"\x22" 代表引号,通过代表十六进制 ASCII 值为 22 的字符。
  • grep -P "a\t+b" file.txt
    • 在某些版本的 GNU Grep 中,用 "\t" 表示制表符(制表符)。由 -P 启用。
  • grep -r "soughtPattern" . --include=*.java
    • 在某些版本的 GNU Grep 中,递归地搜索文件。注意句点代表当前目录。
  • grep -Fxv -f file2.txt file1.txt
    • 输出集合差:file1.txt - file2.txt。使用 -F 来按字面解释搜索词,即非正则表达式,-x 来仅匹配整行,-v 来反转匹配,-f 来从文件获取搜索词。
  • grep -Fx -f file1.txt file2.txt
    • 输出集合交集:file1.txt 中也在 file2.txt 中出现的那些行。
  • grep -P "Sch\xc3\xb6nheit" *
    • 在 unicode UTF-8 编码的文件中搜索德语单词 "Schönheit"。利用 -P 开启 Perl 正则表达式;使用 \x 后面跟着十六进制数来搜索 ö 的 UTF-8 编码,即 C3B6。要找出 UTF-8 文本的十六进制代码,使用一个支持 UTF-8 的纯文本编辑器创建一个包含该文本的文件,然后使用十六进制显示程序(在多个操作系统上都是 hexdump)来查找文本的十六进制代码。UTF-8 编码不要与代码点混淆;ö 的代码点是 F6,而它的 UTF-8 编码是 C3B6。
  • grep -a -i -o "[-_a-z0-9 ]\{4,\}" mybinary.o
    • 在一定程度上模拟 strings 命令,输出至少 4 个字符长度的字符串序列,这些序列符合对允许字符串字符的特定标准。使用 -a 将二进制文件视为文本文件,使用 -o 只输出找到的匹配模式的序列,而不是包含匹配项的行。
  • nice -19 find /etc /var/www -type f -name "*.php" -exec grep -e foreach -e str_replace -e return.*base64_decode {} /dev/null \; >php-possible-malware.txt
    • 然后用这个分析,它首先显示最长的行:cat php-possible-malware.txt | awk '{ print length, $0 }' |sort -n -s -r |head -50 |less
  • perl -ne "print if /\x22hello\x22/" file.txt
    • 这不是真正的 grep 示例,而是一个 Perl 单行程序,如果 Perl 可用,而 grep 不可用,你可以使用它。
GNU Grep 运行的一个例子。

可以从 GNU ftp 服务器 获取旧版本的 GNU grep。

GNU grep 的发布公告在 savannah 组 中。

可以从 git.savannah.gnu.org 获取 GNU grep 的变更日志。

可以在 GnuWin32 项目 以及 Cygwin 中获得用于 MS Windows 的 GNU grep 版本。

[编辑 | 编辑源代码]
华夏公益教科书