为什么当比较两个相同的分支时GitHub会显示更改?

时间:2018-08-09 22:09:15

标签: git github

我已经创建了测试库:https://github.com/Labutin/CompareBranches 让我们尝试克隆和比较两个分支branch_01和branch_02

$ git clone https://github.com/Labutin/CompareBranches.git
Cloning into 'CompareBranches'...
remote: Counting objects: 7, done.
remote: Compressing objects: 100% (3/3), done.
remote: Total 7 (delta 0), reused 0 (delta 0), pack-reused 0
Unpacking objects: 100% (7/7), done.

$ git diff remotes/origin/branch_01..remotes/origin/branch_02 --exit-code
$ echo $?
0

所以,我们有两个相同的分支。

但是,如果我尝试使用Web UI比较两个分支https://github.com/Labutin/CompareBranches/compare/branch_01...branch_02,则会显示1个文件已更改。 为什么? Web UI有什么问题?也许我必须修改URL?

2 个答案:

答案 0 :(得分:2)

这个问题实际上是关于GitHub的-但是我们可以用它来构造一个关于Git的问题。

克隆您的存储库后:

$ git clone https://github.com/Labutin/CompareBranches.git
Cloning into 'CompareBranches'...
remote: Counting objects: 7, done.
remote: Compressing objects: 100% (3/3), done.
remote: Total 7 (delta 0), reused 0 (delta 0), pack-reused 0

我可以查看其中的所有提交:

$ cd CompareBranches
$ git log --all --decorate --oneline --graph
* 5707453 (origin/branch_02) Commit to branch_02
| * c0e3722 (origin/branch_01) commit to branch_01
|/  
* 0e9a4e3 (HEAD -> master, origin/master, origin/HEAD) Initial commit

因此,存在三个提交,它们的实际(但缩写为)名称分别为0e9a4e3c0e37225707453远程跟踪名称 origin/master指的是第一次提交,其他两个远程跟踪名称origin/branch_01origin/branch_02指的是其他两个提交。 / p>

如果我们要求Git比较提交c0e37225707453,则没有区别:

$ git diff c0e3722 5707453

但是,如果我们要求Git比较{commit 0e9a4e35707453,我们会发现这两个commit 是不同的:

$ git diff 0e9a4e3 5707453
diff --git a/README.md b/README.md
index f00f3be..b183451 100644
--- a/README.md
+++ b/README.md
@@ -1 +1,2 @@
-# CompareBranches
\ No newline at end of file
+# CompareBranches
+commit1

由于提交c0e37225707453具有相同的内容,因此将0e9a4e3与任一提交进行比较将显示相同的更改。

git diff命令具有特殊语法

当我们要比较两个提交时,可以运行:

git diff <thing-1> <thing-2>

和Git将事物1与事物2进行比较。尖括号内的部分可以是标识提交的任何内容:例如0e9a4e3之类的原始哈希ID,分支名称或远程跟踪名称。

如果我们运行:

git diff <thing-1>..<thing-2>

Git所做的完全相同:将两者进行比较。

但是,如果我们使用三个点代替两个点:

git diff <thing-1>...<thing-2>

Git做一些特别的事情。 Git不会比较我们命名的两个提交,而是找到一个 third 提交。特别是,Git寻找一个 merge base 提交,这两个命名的提交都将从中下降。我们在上面的git log --graph输出中看到了这一点:这两个提示提交均来自提交0e9a4e3。因此,这是合并的基础,因此,用三个点而不是两个点,这就是Git在比较左侧使用的提交。

右侧本身就是<thing-2>

事实证明,GitHub在这里做同样的事情,这就是GitHub链接中包含三个点的原因:GitHub故意模仿git diff的语法。

答案 1 :(得分:1)

请注意Github URL中的三点。 Github正在执行git diff remotes/origin/branch_01...remotes/origin/branch_02r1..r2r1...r2略有不同。

r1..r2要求r2可以到达的所有提交,而r1可以到达的所有提交。

r1...r2要求“ 两个引用中的任何一个都可访问的所有提交,

让我们在回购中查看这些内容。

A - B [branch_02]
 \
  C [branch_01]

git log branch_01..branch_02给了我们Bbranch_02可以到达A和B,但是branch_01也可以到达A,所以这给了我们B

git log branch_01..branch_02给我们BCbranch_01可以到达ACbranch_02可以到达AB。两个分支都可以到达A,因此将其排除在外。我们剩下BC

有关更多信息,请参见Revision Selection, Double Dot and Triple Dot in Pro Git