当`git diff`显示更改但`git merge`没有任何操作时,合并分支的正确方式是什么?

16

当使用 git diff other_branch 命令显示差异,而 git merge other_branch 命令却无法完成合并时,我被难住了。如何将那些“丢失”的代码合并到我的分支my_branch中呢?

这个SO回答描述了一个类似于我遇到的情况。

o---A---B---C-------G   my_branch
     \       \     /
      --*D*---E---F    other_branch

当我执行操作时,令人惊讶的是 D 中的更改并没有自动合并到 my_branch 中。

git checkout my_branch
git merge other_branch

F 引入到 G

当然,我可以像这样手动创建补丁并将其应用于my_branch

git diff other_branch my_branch > patchfile
git checkout my_branch
patch -p1 < patchfile 

但我希望做得正确,不要弄乱git日志。使用补丁方法,git会将D的更改和我的最新补丁记录为彼此独立发生的(代码变动)。我想简化git log并确保其他人在执行git merge my_branch时不会发生意外问题(悄然而逐渐地)。


2
你尝试将 my_branch 合并到 other_branch 了吗?这样可能会解决差异。如果在 my_branch 中有一些提交被还原,但在 other_branch 中没有,那么你就会陷入这种情况。 - iltempo
@iltempo,在你的评论后,我尝试了合并,确实解决了差异,现在的git diff是干净的。我只需要相信它已经适当地合并了。 - hobs
@iltempo,我并没有有意地撤消 my_branch 中的任何更改,但很可能是因为在检出和编辑以及提交交错的情况下,在 sublime(文本编辑器)中保存时发生了。我需要对所有这些更加小心谨慎。 - hobs
1个回答

16
你好,你似乎同时遇到了两个问题。
假设你的历史记录如所描述的那样:
                my_branch
                    v
----A---B---C-------G   
     \       \     /
      --*D*---E---F
                  ^
             other_branch

为什么差异不为空:

这种情况由你提到的命令产生,即在my_branch上,然后执行git merge other_branch。此操作生成了合并提交G,并将当前分支(my_branch)向前移动,但将other_branch保留在原地。这就是合并总是起作用的方式!当然,在这一点上,my_branchG)和other_branchF)之间仍然会有差异——毕竟它们指向不同的提交。

如果你想让这两个分支相同,可以按以下方式提升other_branch

  1. git checkout other_branch; git merge my_branch——这是一个快进合并,因为GF的后代
  2. [不在other_branch上!] git branch -D other_branch; git branch other_branch my_branch——这将删除other_branch,然后在目前my_branch的位置重新创建它
  3. git checkout other_branch; git reset --hard my_branch——这将移动other_branch到与my_branch目前指向的位置完全相同的地方

执行其中一个步骤后,my_branchother_branch将都指向G


为什么提交D的更改不在my_branchG)中

Git合并历史记录,而不是更改。这通常意味着Git会取出合并的两个分支(如果有的话,还会取出它们最年轻的公共祖先提交,也就是merge-base),并尝试将它们组合在一起。由于Git提交是快照,而不是变更集/增量/差异,因此实际合并中不使用其他提交或更改信息。

使用合并基础,Git进行所谓的三方合并,使用公共祖先来尝试智能解决双方的更改。如果不能,则会中断合并并需要用户解决冲突。

可能发生的情况是在你的历史记录中,要么提交EF还原了(或覆盖了)D的更改——这可能发生在生成E时的合并中,或者在F中进行了实际(手动)更改。

正如你在评论中提到的,你经常在提交之间切换和编辑。这样做会使变更频繁浮动(Git在检出期间携带未提交的更改),这可能很难告诉更改应该去哪里以及它们实际上去了哪里。尝试通过在切换分支之前提交任何更改或使用git stash来缓冲它们来避免这种情况。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接