diff命令学习笔记

只要一直使用着Linux作为主要的工作操作系统,并且经常码代码的话,总有一天会用到diff命令,前面笔者太依赖于git环境了,以致于疏忽了学习这个命令,这段时间又用到了,于是记下来。

读懂diff输出含义

在不加参数,直接对比两个文件的情况下,输出中有三种结果:

  1. a - add,即第二个文件比第一个文件多了。
  2. d - delete,即第二个文件比地一个文件少了。
  3. c - change,即第二个文件同行位置下发生了修改。

以下举例进行说明:
首先建立一个file1.txt:

1
2
3
4
5
6
7
aa
bb
cc
dd
ee
ff
gg

随后建立一个file2.txt:

1
2
3
4
5
6
7
8
aa
bb
cc
zz
dd
ee
ff
gg

使用命令:

1
$ diff file1.txt file2.txt

可以看到输出:

1
2
3a4
> zz

第一行3a4表示变化在第一个文件的第3行,变化的模式是增加(a)的内容,而a后面的4表示变动的内容发生在第二个文件的第4行,增加了>内容zz

换一个理解方法,3a4中间的a表示了模式,而过了第一个文件第3行以及第二个文件的第4行之后,内容又开始匹配了起来。

修改file2.txt:

1
2
3
4
5
6
7
aa
bb
zz
dd
ee
ff
gg

这时候也执行相同的命令,得到:

1
2
3
4
3c3
< cc
---
> zz

第一行3c3表示内容发生在第一个文件的第3行,变化的模式是更改(c)内容,c后面的3表示变化的内容在第二个文件的第3行,细节是分为两部分,---虚线上方是原来的文件变化,原来的cc出去了(<),而zz进来了(>)。

同样换一个理解方法,3c3中间的c表示了模式,而过了第一个文件第3行以及第二个文件的第3行之后,内容又开始匹配了起来。

再次修改file2.txt:

1
2
3
4
5
6
aa
bb
dd
ee
ff
gg

执行相同的diff命令:

1
2
3d2
< cc

第一行3d2表示内容发生在第一个文件的第3行,变化的模式是删除(d)内容,d后面的3表示变化的内容在第二个文件的第3行,原来的cc被删除了(<)。

同样,3d2中间的d表示了模式,而过了第一个文件第3行以及第二个文件的第2行之后,内容又开始匹配了起来。

并排输出模式

并排输出模式提供了对比源文件同行时的情况。

file1.txt内容:

1
2
3
4
5
6
7
8
aa
bb
cc
dd
ee
ff
gg
hh

file2.txt内容:

1
2
3
4
5
6
7
8
9
10
aa
bb
cc
66
99
99
dd
ez
ff
gg

执行命令:

1
$ diff file1.txt file2.txt -y

得到结果:

1
2
3
4
5
6
7
8
9
10
11
aa								aa
bb bb
cc cc
> 66
> 99
> 99
dd dd
ee | ez
ff ff
gg gg
hh <

这个模式下的输出就比较直观了,可以看到4-6行file1.txt由不存在变成file2.txt新增的三行,而第8行发生了改变,第12行的内容被删除了。

上下文模式

还是上述的file1.txtfile2.txt,执行:

1
$ diff -c file1.txt file2.txt

得到:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
*** file1.txt	2017-11-18 10:27:50.036977294 +0800
--- file2.txt 2017-11-18 10:27:58.026110636 +0800
***************
*** 1,8 ****
aa
bb
cc
dd
! ee
ff
gg
- hh
--- 1,10 ----
aa
bb
cc
+ 66
+ 99
+ 99
dd
! ez
ff
gg

这个-c就是指定上下文context的参数,这里由星号包围的数字表示原文件中的1到8行的内容显示,具体有第5行更改()以及第8行的删除(-)动作;然后由减号包围的数字表示变动内容发生在第二个文件的1到10行中,具体是新增了4到6行(+)以及第8行的更改()动作。

统一模式

执行:

1
$ diff -u file1.txt file2.txt

得到:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
--- file1.txt	2017-11-18 10:27:50.036977294 +0800
+++ file2.txt 2017-11-18 10:27:58.026110636 +0800
@@ -1,8 +1,10 @@
aa
bb
cc
+66
+99
+99
dd
-ee
+ez
ff
gg
-hh

统一模式是把上下文模式分开显示前后文件合并在了一起,@@中的-1,8表示第一个文件中的1到8行,+1,10表示第二个文件的1到10行,随后显示具体的变更内容,注意-ee行和+ez行是更改操作。

diff命令也可以用于比较文件夹的不同。

产生补丁以及打补丁

使用命令:

1
$ diff -ruN file1.txt file2.txt > patch1_2.patch

产生补丁文件,随后用cat命令可以查看补丁的内容:

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
--- file1.txt	2017-11-18 10:27:50.036977294 +0800
+++ file2.txt 2017-11-18 10:27:58.026110636 +0800
@@ -1,8 +1,10 @@
aa
bb
cc
+66
+99
+99
dd
-ee
+ez
ff
gg
-hh

完成对file1.txt的打补丁操作:

1
$ patch file1.txt patch1_2.patch

file1.txt的内容就会在打了补丁之后与file2.txt一致。

以上是diff命令的简单介绍以及打补丁操作。