git pull和git pull --rebase之间的区别

Rnd*_*ndm 290 git git-pull

我在某个时候开始使用git,并没有完全理解错综复杂.我在这里的基本问题是找出a git pull和之间的区别git pull --rebase,因为添加--rebase选项似乎没有做一些非常不同的事情:只需要拉动.

请帮助我理解差异.

mvp*_*mvp 301

git pull= git fetch+ git merge反对跟踪上游分支

git pull --rebase= git fetch+ git rebase反对跟踪上游分支

如果你想知道如何git mergegit rebase不同,请阅读此内容.

  • 值得注意的是,`git pull --rebase`与`git fetch`和`git rebase`基本相同,但它并不是*在语义上等同于*.有一些差异,其中一些在这里解释.http://gitolite.com/git-pull--rebase (11认同)
  • 借用Scott Meyers的一句话,这就是我称之为"方便的谎言".无论如何,这是解释它的好方法. (7认同)

Mau*_*pez 232

有时候我们会有一个上游来重新组合我们依赖的分支.这可能是一个大问题 - 如果我们在下游,就会给我们造成混乱的冲突.

神奇的是 git pull --rebase

松散地讲,正常的git pull是这样的(我们将在所有这些示例中使用远程调用的origin和名为foo的分支):

# assume current checked out branch is "foo"
git fetch origin
git merge origin/foo
Run Code Online (Sandbox Code Playgroud)

乍一看,你可能会认为git pull --rebase就是这样做的:

git fetch origin
git rebase origin/foo
Run Code Online (Sandbox Code Playgroud)

但如果上游的rebase涉及任何"压缩"(意味着提交的补丁ID,而不仅仅是他们的订单),这将无济于事.

这意味着git pull --rebase必须做多一点.这是对它的作用和方式的解释.

让我们说你的出发点是这样的:

a---b---c---d---e  (origin/foo) (also your local "foo")
Run Code Online (Sandbox Code Playgroud)

时间过去了,你已经在自己的"foo"上做了一些提交:

a---b---c---d---e---p---q---r (foo)
Run Code Online (Sandbox Code Playgroud)

与此同时,在反社会风潮中,上游维护者不仅重新定义了他的"foo",他还使用了一两次壁球.他的提交链现在看起来像这样:

a---b+c---d+e---f  (origin/foo)
Run Code Online (Sandbox Code Playgroud)

此时的git pull会导致混乱.即使是git fetch; git rebase origin/foo不会削减它,因为一方提交"b"和"c",另一方提交"b + c"会发生冲突.(与d,e和d + e类似).

是什么git pull --rebase呢,在这种情况下,就是:

git fetch origin
git rebase --onto origin/foo e foo
Run Code Online (Sandbox Code Playgroud)

这给你:

 a---b+c---d+e---f---p'---q'---r' (foo)
Run Code Online (Sandbox Code Playgroud)

您可能仍然会遇到冲突,但它们将是真正的冲突(在p/q/r和a/b + c/d + e/f之间),而不是由于b/c与b + c冲突等引起的冲突.

答案取自(并稍加修改):http:
//gitolite.com/git-pull--rebase

  • 这个答案是从http://gitolite.com/git-pull--rebase中逐字复制和粘贴的,并且应该包括该页面上每个许可证的归属. (19认同)
  • 这是最好的答案.您可能希望将最终结果更改为"a --- b + c --- d + e --- f --- p'--- q'--- r'(foo)`因为rebase更改哈希值. (7认同)

Deq*_*ing 38

假设您在本地分支中有两个提交:

      D---E master
     /
A---B---C---F origin/master
Run Code Online (Sandbox Code Playgroud)

在"git pull"之后,将是:

      D--------E  
     /          \
A---B---C---F----G   master, origin/master
Run Code Online (Sandbox Code Playgroud)

在"git pull --rebase"之后,将没有合并点G.注意D和E变为不同的提交:

A---B---C---F---D'---E'   master, origin/master
Run Code Online (Sandbox Code Playgroud)

  • @prgmrDev为什么在F之前插入D和E? (5认同)

dra*_*hnr 10

在最简单的情况下没有碰撞

  • 与底垫:变基您的本地提交ontop的远程端的和不创建一个合并/合并提交
  • without/normal:合并并创建合并提交

也可以看看:

man git-pull

更确切地说,git pull使用给定的参数运行git fetch并调用git merge以将检索到的分支头合并到当前分支中.使用--rebase,它运行git rebase而不是git merge.

另请参阅:
我应该何时使用git pull --rebase?
http://git-scm.com/book/en/Git-Branching-Rebasing

  • 如果发生碰撞? (3认同)

Sag*_*ody 7

因此,了解Merge和Rebase之间的区别非常重要.

Rebases是更改应从层次结构顶部向下传递的方式,而合并是它们向上流回的方式.

有关详细信息,请参阅http://www.derekgourlay.com/archives/428