将本地提交移动到 un-master 本地分支

Move a local commit to un-master local branch

我的情况很复杂,因为我不熟悉git;

我在远程有一个主提交,我在本地创建了一个分支 fix-bug-online-offline-support。 我工作期间,另一个组员改了remote master,我pull了

但我需要将我的分支 fix-bug-online-offline-support 拆分为两个分支;

我已将分支 fix-bug-online-offline-support 的名称更改为 fix-bug-online-offline-support

并且需要将一些提交从 fix-bug-online-support 移动到 fix-bug-offline-support

注意:这两个分支都是本地分支,我有提交的哈希字符串

首先尝试将 origin master 合并到您的本地分支 fix-bug-online-offline-support(一种反向合并)。您的本地分支机构现在已与 origin master 保持同步。现在您可以在该分支中继续您的工作。 您也可以将本地分支拆分为线上线下两个分支。

简短回答:您可以使用 cherry-pick 进行提交并将其放入 fix-bug-offline-supportrebase -i,然后从中删除提交原来的分支。

长答案:据我了解,你有这样的事情

A - B - C - D - E
                L fix-bug-offline-support

并且您想以这样的方式结束

A - C' - E'
 \       L fix-bug-offline-support
  \
    - B' - D'
           L fix-bug-online-support

你可以做到:

git checkout A # replace A with the sha1 of this commit for instance
git checkout -b fix-bug-online-support
git cherry-pick B
git cherry-pick D

此时我们有

A - B - C - D - E
 \              L fix-bug-offline-support
  \
    - B' - D'
           L fix-bug-online-support

所以我们仍然需要从 fix-bug-offline-support 中删除这些提交,我们用

git checkout fix-bug-offline-support
git rebase -i A

并在 rebase -i 命令后出现的文本编辑器中,删除对应于 BD

的行

最后的微妙之处:请注意,我们实际上并不是 "moving" 提交。我们宁愿创建新的提交。这听起来像是一种迂腐的细微差别,但实际上 Git 如果我们没有对这些细微差别给予足够的重视,就会很难理解。所以,澄清一下:

  • 提交是我们项目的快照并且是不可变的(例如:它有一个唯一且永远不会改变的 sha1)
  • 当我们 cherry-pick 时,我们实际上是在其他地方重新应用补丁,并且 git 最终创建了一个带有新 sha1 的新提交(例如:这就是为什么在上图中提交 B 变成了提交 B':它们不是同一个对象)
  • 当我们删除一个提交时同样的事情:实际上 git 将在没有这些补丁的情况下重新应用历史,因此它最终会创建新的提交 C'E'

一个实际的推论是初始提交 E 在我们的操作结束时仍然存在。我们不在乎,因为我们不需要它,而且无论如何它不再可以从分支访问,所以它不会阻止我们。但这是个好消息,因为如果我们发现我们搞砸了,我们仍然可以找回它