【问题标题】:Which order does `git rebase` use to cherry-pick the commits from a merged branch?`git rebase` 使用哪个顺序从合并的分支中挑选提交?
【发布时间】:2018-10-17 05:02:46
【问题描述】:

假设我们有:

C1--C2--C3--C6--C7   <- topic, HEAD
 \   \     /
  \  C4--C5      
   \
    C8--C9           <- master

(我们添加了一个空的file1 并提交给C1,添加了一个空的file2 并提交给C2,等等)。

然后我们这样做:

$ git rebase master

结果是:

C1--C8--C9                         <- master
         \
         C4'--C2'--C5'--C3'--C7'   <- topic, HEAD

我已经创建了一个自动 bash 脚本here,如果你愿意,可以测试它。

据我从 chapter 3.6 in git-scm.com book 了解到,Git 跳过了合并后的结果 C6,因此此处未显示 C6'

我的问题是,Git 使用哪个命令从 topic 分支中挑选?为什么结果是...-C4'--C2'--C5'--C3'--C7' 而不是...-C2'--C3'--C4'--C5'--C7'(按时间顺序)?

【问题讨论】:

标签: git git-rebase


【解决方案1】:

(顺便说一句,感谢您提供的复制器脚本——它在这里非常有帮助。)

顺序在过去有所不同,但通常是通过运行git rev-list 生成的(git log 的姊妹命令,默认情况下只生成哈希 ID)。由于哈希 ID 对人类来说很难,因此使用 git log 来查看顺序通常更容易。

在这种情况下,订单来自:

$ git log --oneline --reverse --no-merges master..topic
5ff52aa C4
aefbb19 C2
0363c27 C5
90aaf5d C3
f953082 (topic) C7

但是,如果我们添加 --topo-order,就像 git rebase 在各种旧 Git 版本中所做的那样,我们会得到:

$ git log --oneline --reverse --topo-order --no-merges master..topic
aefbb19 C2
90aaf5d C3
5ff52aa C4
0363c27 C5
f953082 (topic) C7

在有多个活动提交可供选择的情况下,实际顺序基于提交时间戳。也就是说,Git 正在从提示提交向后进行修订。每当发生合并时,Git 会将所有父级放入优先级队列,从而增加要访问的提交数。优先级队列的默认排序顺序基于提交者时间戳。由于git rebase 没有设置任何其他优先级,因此这是使用的优先级。

(新的、非拓扑排序的顺序是新的 git rebase--helper 内部命令的结果,该命令首次出现在 Git 版本 2.13 中。合并“保留”——实际上是重新创建——变体的git rebase -p 仍然使用拓扑排序。花哨的新标签git rebase -r 不需要拓扑排序。)

【讨论】:

  • 阅读您的回答后,我做了一些测试,直到this test,我想我理解您的回答并解决了我的主要问题。非常感谢,您的回答对我真的很有帮助!
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2016-02-06
  • 1970-01-01
  • 2021-08-18
  • 2018-07-15
  • 2019-11-17
  • 2020-12-11
  • 2021-03-28
相关资源
最近更新 更多