第3章:文本处理三剑客(上):grep命令详解

说实话,在运维和开发这条路上摸爬滚打这么多年,我越来越觉得grep就是那个「平时不起眼,关键时刻救命」的工具。你想想看,每天面对成百上千行日志,眼睛都快看花了,这时候grep就是你的第二双眼睛。

我个人习惯是,不管排查什么问题,第一反应就是grep。不是因为它多高级,而是因为它够快、够准。今天咱们就好好聊聊这个老朋友。

3.1 正则表达式基础

先别急着敲命令。grep的核心能力,说白了就是「模式匹配」。而这个「模式」,就是正则表达式。

正则表达式是什么?我打个比方:它就像一套暗号系统。你告诉grep「帮我找所有以ERROR开头的行」,grep就乖乖去翻日志。这套暗号,就是正则。

3.1.1 基本元字符

元字符 含义 示例
. 匹配任意单个字符 a.c 匹配 abc、adc
* 匹配前一个字符0次或多次 ab*c 匹配 ac、abc、abbc
^ 匹配行首 ^Error 匹配以Error开头的行
$ 匹配行尾 failed$ 匹配以failed结尾的行
[] 匹配括号内任意一个字符 [0-9] 匹配任意数字
[^] 匹配不在括号内的字符 [^0-9] 匹配非数字

嗯,这里要注意:^ 在方括号里外含义完全不同。我在项目中遇到过好几次新人搞混这个,排查半天找不到原因。

3.1.2 扩展正则

基本正则够用,但有时候你会觉得它「不够聪明」。比如你想匹配「abc」或「def」,基本正则写起来很别扭。这时候就需要扩展正则了。

# 基本正则:用 \| 表示或
grep 'abc\|def' log.txt

# 扩展正则:用 | 表示或(更直观)
grep -E 'abc|def' log.txt

我个人强烈建议:直接用 grep -E 或者 egrep。少打几个反斜杠,代码也更好读。

小技巧: 我习惯把 grep -E 写成 alias,叫 grepe。省事。

3.2 grep常用选项详解

好了,正则基础有了,咱们来看看grep那些「救命」的选项。每个选项背后,都有我踩过的坑。

3.2.1 -i:忽略大小写

这个选项太常用了。日志里「Error」和「error」都可能出现,你总不能写两个正则吧?

# 不忽略大小写
grep 'error' app.log
# 只匹配小写error

# 忽略大小写
grep -i 'error' app.log
# 匹配 Error、ERROR、error 等

我曾经排查过一个线上问题,日志里写的是「ERROR」,我愣是grep了「error」半天没结果。后来加了 -i 才找到。嗯,从那以后我养成了习惯:不确定大小写时,先加 -i。

3.2.2 -v:反向匹配

这个选项很有意思。它不是找「匹配的」,而是找「不匹配的」。

# 查看所有非注释行
grep -v '^#' config.conf

# 排除包含 "DEBUG" 的行
grep -v 'DEBUG' app.log

你想想看,有时候日志里90%都是INFO,你只想看ERROR。这时候 -v 就派上用场了。我经常用它来「过滤掉噪音」。

实战场景: 查看nginx错误日志,排除健康检查的请求。
grep -v 'healthcheck' /var/log/nginx/error.log

3.2.3 -c:计数

有时候你不需要看具体内容,只想知道「有多少行匹配」。

# 统计错误次数
grep -c 'ERROR' app.log
# 输出:42

# 统计非空行数
grep -c -v '^$' app.log

我记得有一次监控告警说「错误率飙升」,我第一反应就是 grep -c 'ERROR' 看看具体数量。配合时间范围,很快定位到问题。

注意: -c 只统计行数,不是匹配次数。如果一行里有多个ERROR,也只算1次。

3.2.4 -n:显示行号

这个选项,说白了就是「定位神器」。你找到问题了,但不知道在哪一行,怎么修?

# 显示匹配行及其行号
grep -n 'NullPointerException' app.log
# 输出:187: java.lang.NullPointerException at ...

配合编辑器,直接跳到187行。效率翻倍。

3.2.5 组合使用

这些选项单独用已经很香了,组合起来更是无敌。

# 统计非注释行数(忽略大小写)
grep -c -i -v '^#' config.conf

# 显示所有警告和错误(忽略大小写,显示行号)
grep -in 'error\|warn' app.log

我个人最常用的组合是 -in。为什么?因为日志里大小写不统一,行号又必须看。这两个一组合,基本覆盖了80%的场景。

3.3 知识体系总览

说了这么多,咱们用一张图来总结一下grep的核心逻辑。我画了个SVG,方便你理解。

grep命令知识体系 grep 命令 正则表达式基础 基本元字符:. * ^ $ [] 扩展正则:+ ? | () 常用选项 -i 忽略大小写 -v 反向匹配 -c 计数 -n 显示行号 实战场景 日志错误排查 配置文件分析 数据统计 核心思想:模式匹配 + 选项组合 = 高效日志分析 记住:先想清楚「我要找什么」,再选合适的选项

3.4 避坑指南

最后,分享几个我踩过的坑,希望能帮你少走弯路。

  • 忘记转义特殊字符: 比如你想匹配一个点号 .,直接写 grep '.' 会匹配所有字符。要用 grep '\.'。
  • 大文件不加限制: 几GB的日志直接grep,机器可能会卡死。建议先用 head 或 tail 切分,或者用 grep -m 100 限制匹配行数。
  • 忽略二进制文件: 有时候grep会匹配到二进制文件,输出一堆乱码。加 -I 选项忽略二进制文件。
我的习惯: 每次grep之前,先想清楚「我要找什么模式」、「要不要忽略大小写」、「要不要显示行号」。想清楚了再敲命令,效率翻倍。

好了,grep的基础就聊到这儿。说白了,它就是一把「瑞士军刀」,简单但强大。多用、多练,你会发现它比你想象的更顺手。

可可精品资料库