
一、vi 和 vim:Linux 里的经典文本编辑器
vi 和 vim 都是 Linux/Unix 系统中非常经典的文本编辑器。vi 是原始版本,很多系统默认自带;vim 是从 vi 发展出来的增强版,全称是 Vi IMproved,它兼容 vi 的操作,同时增加了语法高亮、多级撤销、分屏、搜索高亮等功能。
简单理解:vi 是基础款,vim 是加强款。实际运维中更常用 vim,但掌握 vi 的模式和按键逻辑也很重要,因为很多最小化系统里默认可能只有 vi。
vi 和 vim 的区别
| 编辑器 | 说明 |
|---|---|
vi |
原始版本,Unix 系统标配的文本编辑器 |
vim |
增强版 vi,兼容 vi 操作,功能更丰富 |
常见功能对比如下:
| 功能 | vi |
vim |
|---|---|---|
| 语法高亮 | 不支持 | 支持,可使用 syntax on |
| 多级撤销 | 通常较弱 | 支持多级撤销,常用 u / Ctrl + R |
| 多窗口 / 分屏 | 不支持 | 支持 :split / :vsplit |
| 图形界面 | 无 | 支持 gvim |
| 脚本扩展 | 不支持 | 支持 VimScript / Lua |
| 搜索高亮 | 较弱 | 支持 :set hlsearch |
| 命令行历史 | 有限 | 更完整 |
| 鼠标操作 | 不支持 | 可使用 :set mouse=a |
二、vim 的安装和常用工具包
vi 一般系统自带,但 vim 在最小化安装环境里可能没有。如果执行 vim 提示命令不存在,可以先安装。
在 CentOS 7 场景下,可以先备份 yum 源配置文件:
bash
cp /etc/yum.repos.d/CentOS-Base.repo /etc/yum.repos.d/CentOS-Base.repo.bak
下载 yum 源配置文件:
bash
curl -o /etc/yum.repos.d/CentOS-Base.repo https://mirrors.aliyun.com/repo/Centos-7.repo
curl -o /etc/yum.repos.d/epel.repo http://mirrors.aliyun.com/repo/epel-7.repo
安装 vim 和一些常用 Linux 工具:
bash
yum install -y tree vim wget bash-completion bash-completion-extras lrzsz net-tools sysstat iotop iftop htop unzip nc nmap telnet bc psmisc httpd-tools bind-utils nethogs expect
这里不只是安装 vim,还顺带安装了一些运维常用工具。比如 tree 看目录树,wget 下载文件,net-tools 提供 ifconfig 等命令,htop 更直观看进程,lrzsz 方便上传下载文件。
三、vim 的三种模式
vim 最容易卡住的地方就是模式。打开文件后不是马上就能输入文字,因为默认进入的是普通模式。只有切换到插入模式,输入的内容才会真正写进文件。

| 模式 | 进入方式 | 作用 | 退出方式 |
|---|---|---|---|
| 普通模式 | 启动默认进入,或按 Esc |
移动光标、复制、删除、粘贴等 | 不需要单独退出 |
| 插入模式 | i、a、o 等 |
编辑文本内容 | 按 Esc 回到普通模式 |
| 底行模式 | 普通模式下输入 : 或 / |
保存、退出、搜索、替换等 | 执行命令后一般回到普通模式 |
可以把它理解成三种工作状态:
- 普通模式:像"操作遥控器",移动、删除、复制、粘贴。
- 插入模式:像"真正打字",输入文件内容。
- 底行模式:像"下命令",保存、退出、搜索、替换。
四、vim 普通模式常用操作
使用下面命令打开文件后,默认就是普通模式:
bash
vim test.txt
普通模式主要负责光标移动、删除、复制、粘贴、撤销等操作。
光标移动操作
| 操作 | 说明 |
|---|---|
↑ 或 k |
向上移动光标 |
↓ 或 j |
向下移动光标 |
← 或 h |
向左移动光标 |
→ 或 l |
向右移动光标 |
0 或 ^ |
移动光标到行首 |
$ |
移动光标到行尾 |
gg |
移动光标到文件首行 |
G |
移动光标到文件尾行 |
数字 + G |
移动光标到指定行 |
示例:
bash
gg # 跳到第一行
G # 跳到最后一行
20G # 跳到第 20 行
0 # 跳到当前行行首
$ # 跳到当前行行尾
这些操作在修改配置文件时很实用。比如报错提示配置文件第 48 行有问题,就可以在普通模式下输入 48G,快速跳到目标行。
删除、复制和粘贴操作
| 操作 | 说明 |
|---|---|
dd |
删除光标所在行 |
数字 + dd |
从当前行开始删除多行 |
u |
撤销上一步 |
x |
删除光标所在字符,类似 Delete |
X |
删除光标前一个字符,类似 Backspace |
yy |
复制光标所在行 |
p |
粘贴 |
dw |
删除一个单词 |
yw |
复制一个单词 |
示例:
bash
dd # 删除当前行
5dd # 删除当前行开始的 5 行
yy # 复制当前行
3yy # 复制当前行开始的 3 行
p # 粘贴到光标后面
u # 撤销
举个常见场景:修改配置文件前,可以先复制一行再改。
bash
yy
p
这样可以把原配置复制一份,保留参考内容,再修改新复制出来的那一行。
五、vim 插入模式常用操作
普通模式下不能直接输入正文。要进入插入模式,需要按下面这些键:
| 操作 | 说明 |
|---|---|
i |
在当前光标前进入插入模式 |
a |
在当前光标后进入插入模式 |
o |
在当前光标下一行新开一行进入插入模式 |
I |
在当前行行首进入插入模式 |
A |
在当前行行尾进入插入模式 |
O |
在当前光标上一行新开一行进入插入模式 |
常见选择方式:
- 想在当前位置前面补内容,用
i。 - 想在当前位置后面继续写,用
a。 - 想在下一行新增配置,用
o。 - 想在当前行末尾追加内容,用
A。
编辑完成后,一定要按 Esc 回到普通模式,再执行保存或退出。
六、vim 底行模式常用操作
普通模式下输入 : 或 /,就会进入底行模式。它主要用于保存、退出、搜索、显示行号、替换等操作。
| 操作 | 说明 |
|---|---|
:w |
保存 |
:q |
退出 |
:! |
强制操作 |
:wq |
保存并退出 |
:q! |
强制退出,不保存 |
/关键字 |
根据关键字向下搜索 |
n |
搜索下一个匹配项 |
N |
搜索上一个匹配项 |
:noh |
取消搜索高亮 |
:set nu |
显示行号 |
:set nonu |
取消显示行号 |
:%s/old/new/g |
将当前文件中所有匹配的 old 替换为 new |
保存退出的区别
| 命令 | 说明 |
|---|---|
:q |
文件未修改时退出 |
:wq |
保存并退出 |
:q! |
不保存,强制退出 |
如果文件已经修改,再执行 :q 会报错:
bash
E37: 已修改但尚未保存 (可用 ! 强制执行)
原因很简单:vim 发现你改了内容,但没有保存,所以不让你直接退出。此时要么 :wq 保存退出,要么 :q! 放弃修改。
搜索和替换示例
搜索 root:
bash
/root
搜索后,按 n 跳到下一个匹配项,按 N 跳到上一个匹配项。
全文替换:
bash
:%s/old/new/g
这条命令表示把当前文件中所有 old 替换成 new。比如把配置里的 localhost 改成 127.0.0.1:
bash
:%s/localhost/127.0.0.1/g
七、vim 常见问题:异常退出后的 .swp 文件
如果编辑文件时没有正常退出,比如使用 Ctrl + Z 挂起了编辑进程,再次打开同一个文件时,可能会提示存在交换文件,也就是 .swp 文件。
.swp 文件是 vim 用来保存编辑现场的临时文件。它有好处,比如异常断开后可以恢复内容;但如果确认不需要恢复,或者确认没有其他人正在编辑这个文件,就可以删除。
处理步骤:
bash
ls -a
rm -f .test.txt.swp
vim test.txt
注意不要一看到 .swp 就马上删。如果是在生产环境编辑配置文件,先确认没有其他终端正在编辑同一个文件,避免覆盖别人的修改。
八、文件查看命令:head、tail、less、more
Linux 文件经常比较长,尤其是日志文件。不同场景下应该选不同命令:看开头用 head,看结尾用 tail,看大文件用 less,按页简单浏览可以用 more。

九、head:查看文件开头内容
head 用于查看文件开头部分内容,默认显示前 10 行。
| 选项 | 说明 |
|---|---|
-n 数字 |
指定查看文件开头多少行 |
查看 /etc/passwd 前 10 行:
bash
[root@atguigu ~]# head /etc/passwd
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin
sync:x:5:0:sync:/sbin:/bin/sync
shutdown:x:6:0:shutdown:/sbin:/sbin/shutdown
halt:x:7:0:halt:/sbin:/sbin/halt
mail:x:8:12:mail:/var/spool/mail:/sbin/nologin
operator:x:11:0:operator:/root:/sbin/nologin
查看前 5 行有三种常见写法:
bash
[root@atguigu ~]# head -5 /etc/passwd
[root@atguigu ~]# head -n 5 /etc/passwd
[root@atguigu ~]# head -n5 /etc/passwd
输出效果相同:
bash
root:x:0:0:root:/root:/bin/bash
bin:x:1:1:bin:/bin:/sbin/nologin
daemon:x:2:2:daemon:/sbin:/sbin/nologin
adm:x:3:4:adm:/var/adm:/sbin/nologin
lp:x:4:7:lp:/var/spool/lpd:/sbin/nologin
使用场景:快速确认文件格式、查看 CSV 表头、查看日志开头时间、检查配置文件前几行是否正常。
十、tail:查看文件结尾内容
tail 用于查看文件结尾部分内容,默认显示最后 10 行。
| 选项 | 说明 |
|---|---|
-n 数字 |
指定查看文件结尾多少行 |
-f |
跟随查看,实时显示文件尾部新增内容 |
查看 /etc/passwd 最后 10 行:
bash
[root@atguigu ~]# tail /etc/passwd
operator:x:11:0:operator:/root:/sbin/nologin
games:x:12:100:games:/usr/games:/sbin/nologin
ftp:x:14:50:FTP User:/var/ftp:/sbin/nologin
nobody:x:99:99:Nobody:/:/sbin/nologin
systemd-network:x:192:192:systemd Network Management:/:/sbin/nologin
dbus:x:81:81:System message bus:/:/sbin/nologin
polkitd:x:999:998:User for polkitd:/:/sbin/nologin
sshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologin
postfix:x:89:89::/var/spool/postfix:/sbin/nologin
chrony:x:998:996::/var/lib/chrony:/sbin/nologin
查看最后 5 行:
bash
[root@atguigu ~]# tail -5 /etc/passwd
[root@atguigu ~]# tail -n 5 /etc/passwd
[root@atguigu ~]# tail -n5 /etc/passwd
输出示例:
bash
dbus:x:81:81:System message bus:/:/sbin/nologin
polkitd:x:999:998:User for polkitd:/:/sbin/nologin
sshd:x:74:74:Privilege-separated SSH:/var/empty/sshd:/sbin/nologin
postfix:x:89:89::/var/spool/postfix:/sbin/nologin
chrony:x:998:996::/var/lib/chrony:/sbin/nologin
实时查看文件尾部更新:
bash
[root@atguigu ~]# tail -f /etc/passwd
tail -f 很适合看日志,因为日志通常都是追加到文件尾部。比如排查 Nginx 访问日志:
bash
tail -f /var/log/nginx/access.log
再比如看系统日志:
bash
tail -f /var/log/messages
执行后命令不会自动退出,会一直等文件追加新内容。要退出可以按 Ctrl + C。
十一、less:支持翻页和搜索的文件浏览器
less 可以浏览文件内容,支持向上翻页、向下翻页、搜索、跳转到指定行。查看大文件时,less 比直接 cat 更舒服。
| 操作或选项 | 说明 |
|---|---|
less -N 文件 |
查看文件并显示行号 |
q |
退出 |
PageDown / 空格 / f |
向下翻一页 |
PageUp / b |
向上翻一页 |
/字串 |
向下搜索指定字符串 |
?字串 |
向上搜索指定字符串 |
n |
跳到下一个匹配项 |
N |
跳到上一个匹配项 |
g |
跳转到第一行 |
G |
跳转到最后一行 |
数字g |
跳转到指定行 |
查看文件并显示行号:
bash
less -N /etc/passwd
进入 less 后搜索 sshd:
bash
/sshd
按 n 继续找下一个,按 q 退出。
使用场景:日志文件很大、不想一次性刷屏、需要反复上下翻页搜索时,用 less 更合适。
十二、more:按页查看文件内容
more 和 less 类似,也可以按页查看文件内容。它比 cat 更适合看长文件,但灵活性一般不如 less。
| 操作 | 说明 |
|---|---|
空格 |
向下翻一页 |
Enter |
向下翻一行 |
q |
退出 |
b |
返回上一页 |
= |
输出当前行号 |
:f |
输出文件名和当前行号 |
示例:
bash
more /etc/passwd
简单对比:
| 命令 | 适合场景 |
|---|---|
cat |
文件很短,一次性打印 |
more |
简单分页查看 |
less |
大文件浏览、搜索、上下翻页 |
head |
只看开头 |
tail |
只看结尾或实时日志 |
十三、wc:统计行数、单词数、字节数
wc 是 word count 的缩写,可以统计指定文件的行数、单词数和字节数。
| 选项 | 说明 |
|---|---|
-l |
只统计行数 |
-w |
只统计单词数 |
-c |
只统计字节数 |
准备测试文件:
bash
[root@atguigu ~]# cat a.txt
11111111111
22222222222
33333333333
默认统计:
bash
[root@atguigu ~]# wc a.txt
3 3 36 a.txt
这三个数字分别表示:行数、单词数、字节数。
只统计行数:
bash
[root@atguigu ~]# wc -l a.txt
3 a.txt
只统计单词数:
bash
[root@atguigu ~]# wc -w a.txt
3 a.txt
只统计字节数:
bash
[root@atguigu ~]# wc -c a.txt
36 a.txt
实际排障里,wc -l 用得很多。比如统计日志里有多少行报错:
bash
grep "ERROR" app.log | wc -l
统计当前目录下有多少个 .conf 文件:
bash
ls *.conf | wc -l
十四、which:查询命令位置
which 用来查询命令所在位置,它会在环境变量 $PATH 设置的目录里查找符合条件的可执行文件。
查询多个命令的位置:
bash
[root@atguigu ~]# which cd head tail wc shutdown
/usr/bin/cd
/usr/bin/head
/usr/bin/tail
/usr/bin/wc
/usr/sbin/shutdown
如果查询不存在的命令,会提示找不到:
bash
[root@atguigu ~]# which aaa
/usr/bin/which: no aaa in (/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/root/bin)
使用场景:当一台机器上可能安装了多个同名命令,或者脚本执行结果和预期不一样时,可以先用 which 看看当前执行的是哪个路径下的命令。
十五、whereis:查询命令及相关文件位置
whereis 可以查询命令以及相关文件位置,通常用于查找二进制文件、源代码文件和 man 手册页。
| 选项 | 说明 |
|---|---|
-b |
只查找二进制文件 |
-m |
只查找说明文件,也就是 man 手册 |
查询 cd 命令相关位置:
bash
[root@atguigu ~]# whereis cd
cd: /usr/bin/cd /usr/share/man/man1/cd.1.gz /usr/share/man/mann/cd.n.gz
只查询二进制文件位置:
bash
[root@atguigu ~]# whereis -b cd
cd: /usr/bin/cd
只查询 man 手册页位置:
bash
[root@atguigu ~]# whereis -m cd
cd: /usr/share/man/man1/cd.1.gz /usr/share/man/mann/cd.n.gz
which 和 whereis 的区别可以这样记:
| 命令 | 重点 |
|---|---|
which |
查当前 shell 实际会执行哪个命令 |
whereis |
查命令相关文件,比如二进制文件、手册文件 |
十六、diff:逐行比较文件差异
diff 用来比较两个文本文件的差异,它会逐行比较内容,告诉我们哪里新增、删除、修改。
常见标记:
| 标记 | 英文 | 含义 |
|---|---|---|
a |
add | 文件 1 的某行后面需要添加内容,才能变成文件 2 |
d |
delete | 文件 1 的某些内容需要删除,才能变成文件 2 |
c |
change | 文件 1 的某些内容需要修改,才能变成文件 2 |
< |
- | 第一个文件中的内容 |
> |
- | 第二个文件中的内容 |
几个标记例子:
| 示例 | 说明 |
|---|---|
5a6 |
在文件 1 第 5 行后添加内容,对应文件 2 第 6 行 |
3c3 |
文件 1 第 3 行需要修改为文件 2 第 3 行 |
9d6 |
文件 1 第 9 行相关内容需要删除,对应文件 2 第 6 行 |
准备两个文件:
bash
[root@atguigu ~]# cat a.txt
11111111111
22222222222
33333333333
44444444444
[root@atguigu ~]# cat b.txt
11111111111
22222222222
33333333333
aaaaaaaaaaa
bbbbbbbbbbb
ccccccccccc
比较文件差异:
bash
[root@atguigu ~]# diff a.txt b.txt
4c4,6
< 44444444444
---
> aaaaaaaaaaa
> bbbbbbbbbbb
> ccccccccccc
解释一下:
4c4,6表示第一个文件第 4 行需要修改,才能对应第二个文件第 4 到第 6 行。< 44444444444是第一个文件里的内容。> aaaaaaaaaaa、> bbbbbbbbbbb、> ccccccccccc是第二个文件里的内容。
可以把 diff 理解成"告诉你怎么把文件 A 改成文件 B"。如果文件 A 少了内容,就会提示 add;如果文件 A 多了内容,就会提示 delete;如果内容不一样,就会提示 change。
十七、vimdiff:用 vim 方式高亮比较文件
vimdiff 是 vim 编辑器提供的文件差异比较工具,适合做配置对比、脚本版本对比、代码合并等工作。
使用方式:
bash
[root@atguigu ~]# vimdiff a.txt b.txt
它的功能类似:
bash
vim -d a.txt b.txt
进入后会以 vim 的方式打开两个文件,并高亮显示不同内容。在里面仍然可以使用 vim 操作,比如移动、搜索、保存、退出。
退出时要注意:如果打开了两个窗口,每个窗口都需要退出。可以在每个窗口里执行:
bash
:q
如果修改了内容,使用:
bash
:wq
如果不想保存修改:
bash
:q!
使用场景:比如改了 nginx.conf,想和备份文件对比:
bash
vimdiff nginx.conf nginx.conf.bak
相比纯文本 diff,vimdiff 更直观,适合人工检查差异。
十八、sort:按行排序
sort 用于针对文本文件内容进行排序,默认以行为单位处理。它默认不会修改原文件,只会把排序后的结果输出到屏幕。
| 选项 | 说明 |
|---|---|
-n |
按数值大小排序 |
-k |
按指定列排序 |
-r |
倒序排序,默认是升序 |
-t '分隔字符' |
指定字段分隔符,默认是空格 |
-u |
排序后去重 |
示例演示:默认排序和数字排序
准备测试文件:
bash
[root@atguigu ~]# cat a.txt
100
01
12
23
45
21
36
200
002
直接使用 sort:
bash
[root@atguigu ~]# sort a.txt
002
01
100
12
200
21
23
36
45
这个结果看起来有点奇怪,原因是 sort 默认按字符排序,不是按数字大小排序。字符排序时,会从左到右比较字符,所以 100 会排在 12 前面。
按数值大小排序,需要加 -n:
bash
[root@atguigu ~]# sort -n a.txt
01
002
12
21
23
36
45
100
200
示例演示:按第二列排序
修改文件内容:
bash
[root@atguigu ~]# cat a.txt
100 a
01 f
12 s
23 w
45 x
21 z
36 e
200 f
002 c
按第二列排序:
bash
[root@atguigu ~]# sort -k2 a.txt
100 a
002 c
36 e
01 f
200 f
12 s
23 w
45 x
21 z
因为默认分隔符是空格,所以 sort -k2 能识别第二列。
示例演示:指定分隔符排序
如果文件内容变成下面这样,字段之间用 - 分隔:
bash
[root@atguigu ~]# cat a.txt
100-a
01-f
12-s
23-w
45-x
21-z
36-e
200-f
002-c
这时需要用 -t 指定分隔符:
bash
[root@atguigu ~]# sort -t '-' -k2 a.txt
100-a
002-c
36-e
01-f
200-f
12-s
23-w
45-x
21-z
按第二列倒序排序:
bash
[root@atguigu ~]# sort -t '-' -rk2 a.txt
21-z
45-x
23-w
12-s
200-f
01-f
36-e
002-c
100-a
注意:-r 是倒序,-k2 是按第 2 列排序,-t '-' 是指定 - 作为分隔符。
示例演示:按多列排序
准备学生成绩数据:
bash
[root@atguigu ~]# cat a.txt
张三:18:100
李四:25:98
王五:19:100
赵六:25:100
田七:25:90
崔八:19:95
小明:25:85
小红:18:90
按第二列年龄倒序排序,如果年龄相同,再按第三列成绩倒序排序:
bash
[root@atguigu ~]# sort -t ':' -rn -k2 -k3 a.txt
赵六:25:100
李四:25:98
田七:25:90
小明:25:85
王五:19:100
崔八:19:95
张三:18:100
小红:18:90
这里的参数含义:
-t ':':使用冒号作为分隔符。-r:倒序。-n:按数字排序。-k2 -k3:先按第 2 列,再按第 3 列排序。
这个例子很接近实际业务数据排序。比如按年龄排序、按分数排序、按访问次数排序,本质上都是找准分隔符和字段。
示例演示:IP 地址排序的易错点
准备 IP 和 MAC 数据:
bash
[root@atguigu ~]# cat b.txt
192.168.3.1 00:0F:AF:81:19:1F
192.168.3.2 00:0F:AF:85:6C:25
192.168.3.3 00:0F:AF:85:70:42
192.168.2.20 00:0F:AF:85:55:DE
192.168.2.21 00:0F:AF:85:6C:09
192.168.2.22 00:0F:AF:85:5C:41
192.168.0.151 00:0F:AF:85:6C:F6
192.168.0.152 00:0F:AF:83:1F:65
192.168.0.153 00:0F:AF:85:70:03
192.168.1.10 00:30:15:A2:3B:B6
192.168.1.11 00:30:15:A3:23:B7
192.168.1.12 00:30:15:A2:3A:A1
192.168.1.1 00:0F:AF:81:19:1F
192.168.2.2 00:0F:AF:85:6C:25
192.168.3.3 00:0F:AF:85:70:42
192.168.2.20 00:0F:AF:85:55:DE
192.168.1.21 00:0F:AF:85:6C:09
192.168.2.22 00:0F:AF:85:5C:41
192.168.0.151 00:0F:AF:85:6C:F6
192.168.1.152 00:0F:AF:83:1F:65
192.168.0.153 00:0F:AF:85:70:03
192.168.3.10 00:30:15:A2:3B:B6
192.168.1.11 00:30:15:A3:23:B7
192.168.3.12 00:30:15:A2:3A:A1
如果想按 IP 的第三段和第四段倒序排序,容易写成:
bash
[root@atguigu ~]# sort -t '.' -rn -k3 -k4 b.txt
这种写法可能出现第三列排序有效,但第四列排序不准确的问题。原因是使用了自定义分隔符后,字段范围如果不写清楚,sort 可能会把后续内容也纳入比较范围。
更稳妥的写法是:
bash
[root@atguigu ~]# sort -t '.' -rn -k3,3 -k4,4 b.txt
-k3,3 表示排序字段从第 3 列开始,到第 3 列结束,只比较第 3 列。-k4,4 同理,只比较第 4 列。
这个写法非常重要。以后做多列排序时,特别是分隔符不是默认空格时,建议写成 -k字段,字段,范围更清楚。
示例演示:找 /etc 目录下最大的 10 个文件
bash
[root@atguigu ~]# ll /etc | sort -rn -k5 | head
-rw-r--r--. 1 root root 670293 6月 7 2013 services
-rw-r--r--. 1 root root 19710 6月 13 15:20 ld.so.cache
-rw-r--r--. 1 root root 12288 6月 10 15:59 aliases.db
-rw-r--r--. 1 root root 7274 6月 10 15:39 kdump.conf
-rw-r--r--. 1 root root 6545 4月 1 2020 protocols
-rw-r--r--. 1 root root 5725 8月 6 2019 DIR_COLORS.256color
-rw-r--r--. 1 root root 5171 10月 31 2018 man_db.conf
-rw-r--r--. 1 root root 5122 10月 2 2020 makedumpfile.conf.sample
-rw-r--r--. 1 root root 5090 8月 6 2019 DIR_COLORS
-rw-r--r--. 1 root root 4669 8月 6 2019 DIR_COLORS.lightbgcolor
这条命令拆开看:
bash
ll /etc # 列出 /etc 下文件
sort -rn -k5 # 按第 5 列文件大小进行数字倒序排序
head # 取前 10 行
实际排查磁盘空间时也经常会用类似思路:先列出文件,再按大小排序,再取前几条。
十九、uniq:去掉重复行
uniq 是 unique 的缩写,用于检查和删除文本文件中重复出现的行。

| 选项 | 说明 |
|---|---|
-c |
在每行前面显示该行重复出现的次数 |
示例演示:相邻重复行去重
准备文件:
bash
[root@atguigu ~]# cat a.txt
a
a
a
a
b
b
b
c
c
c
c
d
d
使用 uniq 去重:
bash
[root@atguigu ~]# uniq a.txt
a
b
c
d
统计重复次数:
bash
[root@atguigu ~]# uniq -c a.txt
4 a
3 b
4 c
2 d
这个例子能正常去重,是因为相同内容都挨在一起:a 和 a 相邻,b 和 b 相邻。
易错点:uniq 只能处理相邻重复行
如果文件内容变成乱序:
bash
[root@atguigu ~]# cat a.txt
a
a
a
a
b
b
b
d
c
c
c
a
b
c
a
b
d
c
c
c
d
d
直接使用 uniq:
bash
[root@atguigu ~]# uniq a.txt
a
b
d
c
a
b
c
a
b
d
c
d
可以看到,结果并没有真正全局去重。原因是 uniq 只会合并相邻重复行,不会在整个文件里"到处找相同内容"。
正确做法是先用 sort 排序,把相同内容排到一起:
bash
[root@atguigu ~]# sort a.txt
a
a
a
a
a
a
b
b
b
b
b
c
c
c
c
c
c
c
d
d
d
d
再配合 uniq -c 统计:
bash
[root@atguigu ~]# sort a.txt | uniq -c
6 a
5 b
7 c
4 d
这个组合非常常用:
bash
sort a.txt | uniq -c
如果想按出现次数倒序排列,可以继续接一次 sort:
bash
sort a.txt | uniq -c | sort -rn
二十、组合命令示例
这些命令单独看都不难,但真正好用的是组合起来。
操作示例:统计日志中 ERROR 出现次数
bash
grep "ERROR" app.log | wc -l
含义:先筛出包含 ERROR 的行,再统计行数。
操作示例:实时查看服务日志
bash
tail -f /var/log/messages
含义:持续查看日志尾部新增内容,排查服务启动失败或系统异常时很常用。
操作示例:查看文件开头和结尾
bash
head -n 20 access.log
tail -n 50 access.log
含义:前者看前 20 行,后者看最后 50 行。
操作示例:统计重复 IP
假设 ip.txt 里每行是一个 IP:
bash
sort ip.txt | uniq -c | sort -rn
含义:
bash
sort ip.txt # 把相同 IP 排到一起
uniq -c # 统计每个 IP 出现次数
sort -rn # 按出现次数倒序排列
操作示例:比较配置文件差异
bash
diff nginx.conf nginx.conf.bak
vimdiff nginx.conf nginx.conf.bak
diff 适合快速看文本差异,vimdiff 适合人工打开对比并处理差异。
二十一、注意事项和易错点
-
vim打开文件后默认是普通模式,不能直接输入正文。要先按i、a、o进入插入模式。 -
修改文件后不能直接
:q退出。需要保存就用:wq,不保存就用:q!。 -
.swp文件不要随手乱删。确认没有其他终端正在编辑同一个文件,再删除。 -
head和tail默认都是 10 行,一个看开头,一个看结尾。 -
tail -f不会自动退出,需要按Ctrl + C停止。 -
大文件优先用
less,不要直接cat刷屏。 -
sort默认按字符排序,数字排序要加-n。 -
自定义分隔符排序时,用
-t指定分隔符,用-k指定列。 -
多列排序时,推荐写成
-k3,3 -k4,4这种明确字段范围的形式。 -
uniq只处理相邻重复行,全局去重通常先sort再uniq。
二十二、总结
| 场景 | 常用命令 |
|---|---|
| 编辑文件 | vim |
| 看文件开头 | head |
| 看文件结尾 | tail |
| 实时看日志 | tail -f |
| 翻页看大文件 | less / more |
| 统计行数、单词数、字节数 | wc |
| 查命令位置 | which / whereis |
| 比较文件差异 | diff / vimdiff |
| 排序 | sort |
| 去重和统计重复次数 | uniq |