- c - 在位数组中找到第一个零
- linux - Unix 显示有关匹配两种模式之一的文件的信息
- 正则表达式替换多个文件
- linux - 隐藏来自 xtrace 的命令
我有一棵树:
/--b1---b2 <-- topic b
/
a1---a2 <-- topic a
其中“b”取决于“a”。然后我意识到我需要做一些与主题“a”相关的更改才能继续“b”,但我想在“b”上做这些更改作为“b”的正常开发过程:
/--b1---b2---a3---a4---b3---b4---a5---b5 <-- topic b
/
a1---a2 <-- topic a
然后,当我想在“b”上完成的事情完成时,我希望我的树看起来像这样:
/--b1---b2--------m---b3'---b4'---b5' <-- topic b
/ /
a1---a2---a3'---a4'---a5' <-- topic a
就好像我真的在“a”上做了所有更改,然后在“b”上 merge 它们,然后在“b”上继续。
我知道我可以手动执行此操作:
1- rebase/cherry-pick 'a' 从分支 'b' 提交到 'a'
2- 在“b”上创建时间分支“b-tmp”。
3- 将分支 'b' 重置为 'b2'。
4- 将 'a' merge 到 'b' 上。
5- rebase/cherry-pick 'b' 从 'b-tmp' 提交到 'b'。
6- 删除分支 'b-tmp'。
我可以创建一些脚本来执行此操作,我只是想知道除了这 6 个步骤之外是否还有更好的方法/想法。
最佳答案
首先让我说我宁愿经常集成主题分支(尽早集成,经常构建......敲响了钟声?)。所以实际上,当最终应该对 a 进行更改时,我会返回,在 a 上进行更改,并在 之上重新设置 b一个。
如果 a 出于某些其他目的需要保持稳定,我会创建一个 a-for-b 分支来临时包含工作,然后 rebase b 最重要的是。
如果您真的必须在分支“b”中处理“topic-a”更改,这就是我要做的。
注意:包含截屏视频
这是一个简单的工作树,带有问题的布局:
mkdir /tmp/q
cd /tmp/q
git init .
touch f
git add f
git commit -am initial
git checkout -b a; for a in a{1,2}; do echo $a>$a; git add $a; git commit -am $a; git tag $a; done
git checkout -b b; for a in b{1,2} a{3,4} b{3,4} a5 b5; do echo $a>$a; git add $a; git commit -am $a; git tag $a; done
git show-branch
git checkout -b a_new a # for safety, work on a clone of branch a
git reset --hard b # start by moving it to the end of the b branch
git status # (just show where we are)
git log --oneline
git rebase -i a # rebase it on top of the original branch a
# not shown: delete every line with non-branch-a commits (b1-b5)
# see screencast
git log --oneline # (just show where we are again)
git checkout -b b_new b # for safety, work on a clone of branch b
git log --oneline # (just show where we are again: the end of branch b)
git rebase -i a_new # this time, rebase it on top of the new branch a_new
git log --oneline # (check results)
git show-branch b_new a_new
我们现在可以做一个之前/之后的树比较:
sehe@natty:/tmp/q$ git show-branch a b
! [a] a2
! [b] b5
--
+ [b] b5
+ [b^] a5
+ [b~2] b4
+ [b~3] b3
+ [b~4] a4
+ [b~5] a3
+ [b~6] b2
+ [b~7] b1
++ [a] a2
sehe@natty:/tmp/q$ git show-branch a_new b_new
! [a_new] a5
* [b_new] b5
--
* [b_new] b5
* [b_new^] b4
* [b_new~2] b3
* [b_new~3] b2
* [b_new~4] b1
+* [a_new] a5
for name in a b;
do
git branch -m $name ${name}_old &&
git branch -m ${name}_new $name
done
git branch -D a_old b_old # when sure
我特意选择对演示进行不冲突的更改。当然在现实生活中你会遇到 merge 冲突。使用 git mergetool
和 git rebase --continue
.
如果您的更改是卫生的并且确实属于它们各自的主题分支,那么冲突应该很少并且很容易解决。 否则,是时候修改您的分支方案了(参见 Martin Fowler e.a.)
回应
You also say that "when there are changes that should go onto 'a' eventually, I'd go back, do the changes on 'a', and rebase 'b' on top of 'a'". I'm not sure I understand this also. Could you explain?
我的意思是无论如何我都会尝试在 a 分支上进行 a3、a4、a5 修订,并将 b rebase 到那个分支上,所以
<-- this is the
<强> Merge Early/Soon/Frequently
mantra
这里是“开始”点,但适应了我理想化的工作流程。请注意,此替代结果的最终结果已经完全在上面“将提交重新组织到其主题分支”下显示的所有杂耍之后最终得到的结果!
mkdir /tmp/q
cd /tmp/q
git init .
touch f
git add f
git commit -am initial
git checkout -b a; # no change
echo a1>a1; git add a1; git commit -am a1
echo a2>a2; git add a2; git commit -am a2
git checkout -b b; # start off the a branch
echo b1>b1; git add b1; git commit -am b1
echo b2>b2; git add b2; git commit -am b2
git checkout a # go back to the a branch for a3 and a4
echo a3>a3; git add a3; git commit -am a3
echo a4>a4; git add a4; git commit -am a4
git checkout b
git rebase a # here is the magic: rebase early
echo b3>b3; git add b3; git commit -am b3
echo b4>b4; git add b4; git commit -am b4
git checkout a # go back to the a branch for a5
echo a5>a5; git add a5; git commit -am a5
git checkout b
git rebase a # again: rebase early
echo b5>b5; git add b5; git commit -am b5
git show-branch
注意实际上返回 a 分支提交 a3/a4/a5 提交并不难:
git add -i
或 git guis 中的类似内容或例如 vim fugitive
) git checkout b
)2 只要它们不与 a..b 的其他更改冲突;在那种情况下你会git stash
首先和git stash apply
在 a 分支上
关于git - 将提交从一个分支移动到另一个分支,然后将它们 merge 回去,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/7545982/
我从一个 Mercurial 存储库开始,它有多个我试图 merge 到其中的子存储库,就好像它们一直是主存储库的一部分一样。它们从一开始就不应该是子存储库。 我整理了一个将旧历史转换为单个存储库的过
假设我有一个主线分支和一个功能分支。我已经多次将主线分支 merge 到功能分支中,但只有少数非常小的 merge 冲突。我想清理历史,以便最后只有一个 merge 。执行此操作的最佳方法是什么? 最
首先我使用heapq.merge创建了a&b的两个结果,但是在mergea&b之后,我发现a的列表是空的。 >>> a=merge([1,2],[3,4]) >>> b=merge([4,5],[6,
我和我的团队正在使用远离主轨道 (origin/dev) 的远程分支 (origin/our_feature_branch) 开发一项功能。 Gerrit用于审查等。 使用 git merge ori
这个问题在这里已经有了答案: Is there a way to merge with Strategy "ours" without producing a new commit? (1 个回答)
GitLab 无法自动 merge 请求。所有 merge 请求都会收到消息“此 merge 请求包含必须解决的 merge 冲突。您可以在命令行上手动尝试” 消息似乎不正确,我通过使用“git br
git 有没有办法在不 merge 文件的情况下 merge 两个分支?换句话说就是绘制 merge 箭头。 假设我有分支 A 和 B。我需要将分支 B merge 到 A,但不需要 B 中的所有更改
我想使用提供 git 集成的流行的开源问题跟踪器 (Redmine)。不幸的是,跟踪器中的每个项目只能与一个 git repo 相关联。在跟踪器中创建多个项目不是我理想的设置。 考虑到这一点,我尝试使
在我们的存储库中,我们遵循基于 git-flow 的工作流程。我们有一个已完成的发布(安装在生产环境中),因此发布分支已 merge 到主分支中。 B---C---D---E [release
git merge 命令有一个执行快进 merge 的选项,但这不是我想要的,因为如果它不能执行快进 merge ,它会使用普通 merge . 是否有一个 git 命令仅执行快进 merge (从跟
尝试合并 TFS2008 时出现此错误。源分支或目标分支上都没有挂起的更改。 TF14083: The item {0} has a pending merge from the current me
为了更好地理解这些操作,我想知道 github 或 gitlab 到底是如何 merge 这些请求的。当压缩、 rebase 、 merge ......时详细执行哪些 git 命令? 最佳答案 PR
为了更好地理解这些操作,我想知道 github 或 gitlab 到底是如何 merge 这些请求的。当压缩、 rebase 、 merge ......时详细执行哪些 git 命令? 最佳答案 PR
我试图将提交的一部分从默认分支(不是所有文件和其他文件的部分) merge 到一个命名分支。我试过 graft ,但它只需要整个提交,而没有给我选择的机会。这将如何完成? 例子: A---B---C-
我正在进行 merge ,此时我已准备好提交,但我在 TortoiseHg 中的提交对话框显示许多文件已修改,但是当我与 parent 进行比较时,它说所有文件都是二进制相等的。 我没有也从未有过 e
我已经尝试了以下几种变体,但我仍然遇到错误。有什么办法可以解决这个问题。 DB2 10.1(DB2 for z/OS V10) 对于以下 MERGE INTO TRGT t USING SRC s O
我的数据库模型有用户和 MAC 地址。一个用户可以有多个MAC地址,但一个MAC只能属于一个用户。如果某个用户设置了他的 MAC,并且该 MAC 已经链接到另一个用户,则现有关系将被删除,并在新所有者
假设我有一个新功能,所以我创建了一个新分支。这个分支是一个会持续很长时间的副项目,所以我最终将 master merge 回它以使其保持最新状态。这已经发生了 50 次,因为我一直在更新它并消除该功能
过去几个小时我在 Mercurial 中进行了一次巨大的 merge 。 merge 131 个文件后,我的 merge 工具 meld 崩溃,显示 python 回溯。在尝试退出 meld 时,我无
我有一个关于 git merge 的问题。假设我的存储库中有两个分支(本地和远程):master 和 test。当我在测试分支上工作时,主分支被其他人更新了。在终端中,我写: git checkout
我是一名优秀的程序员,十分优秀!