gpt4 book ai didi

git - Git merge 会影响“merge ”分支吗?

转载 作者:行者123 更新时间:2023-12-03 02:44:53 24 4
gpt4 key购买 nike

我工作的公司一直在尝试Git工作流,它具有三个主要分支(开发,测试版,母版)以及各个功能分支。这涉及将功能分支彼此独立地合并为“ develop”和“ beta”,然后定期将“ beta”合并为“ master”以进行发布。

问题是:当我们将功能分支合并到“开发”时,似乎会影响功能分支的提交历史,因此,当我们尝试将同一分支合并到“测试版”时,它还将包括“开发”中的所有提交,这不是我们想要的。

有人知道这是怎么回事吗?是否可以将一个分支合并到另外两个分支中而不包含任何不需要的提交?我们的工作流程有哪些变化可以阻止这种情况?我知道没有代码示例或任何东西,但实际上不是那种类型的问题,我不确定如何还能提供更多有用的信息。

谢谢!

最佳答案

从一个基本的意义上说,合并操作实际上不会影响任何分支。 (它的确会进行新的提交,并以通常的方式影响该分支。)Git的窍门是将以下五个同时出现的想法牢记在心:


在Git中重要的是提交及其父链接。分支名称大多只是分散注意力(但请参阅第2点和第3点)。
分支名称只是特定提交的名称,我们称其为该分支的尖端提交。
进行新提交时,Git会以当前提交作为其父提交来写入新提交。1如果新提交具有多个父提交(请参阅下一点),则当前提交将成为其第一父提交。无论如何,Git然后都会更新分支名称以指向新的提交。这就是分支“增长”的方式。
合并提交是具有两个(或更多)父提交的提交。就像以前一样,这是“作为名词合并”。
进行合并的行为(我的意思是合并提交)涉及进行三路合并操作,然后照常进行新的提交,不同之处在于新提交具有两个(或多个)父级。 “额外的”父母是合并的提交。2


合并动作-“作为动词合并”-使用通过以上五个要点建立的历史记录。 Git找到三个提交:


当前提交,也称为HEAD。 (这很简单。)
要合并的提交:为您传递给git rev-parse的参数提供git merge的任何ID。分支名称只是找到分支提示的提交。
合并基础。这就是提交历史记录的来源,这就是为什么您需要绘制图形片段的原因。


任意两个提交的合并基础松散地定义为“图形返回的(第一个)点”:

...--o--*--o--o--o     <-- branch1
\
o--o--o--o <-- branch2


名称 branch1指向顶行上最尖端的提交。名称 branch2指向底行上的提示提交。这两个提交的合并基础是标记为 * .3的一个

为了执行合并动作,Git然后根据两个技巧对合并基础提交 git diff进行差异化(如 *所示),给出两个差异。然后Git合并差异,每次更改仅获取一个副本:如果您(在 branch1上)和他们(在 branch2上)都将 color改为 colour,则Git只需换一次。

存储在工作树中的结果源将成为合并提交的树。请注意,到目前为止,将 README合并到 branch2还是将 branch1合并到 branch1都无关紧要:我们将获得相同的合并基础,并且具有相同的两个提示提交,因此获得相同的两个差异,并以相同的方式组合这两个差异,以达到相同的工作树。但是,现在我们与两个父级一起进行实际的合并提交,而现在我们在哪个分支上也很重要。如果在 branch2上,则在 branch1上进行新的提交,并将名称 branch1提前:

...--o--o--o--o--o---M   <-- branch1
\ /
o--o--o--o <-- branch2


新的合并提交有两个父对象:一个是 branch1的旧提示,另一个是 branch1的提示。

因为我们现在有了一个新图,所以以后的 branch2将找到一个新的合并基础。假设我们在两个分支上都进行了多次提交:

...--o--o--o--o--o---M--o--o     <-- branch1
\ /
o--o--o--*---o--o--o <-- branch2


如果现在我们要求合并两个分支,则Git首先找到基础。这是两个分支上都最接近这两个技巧的提交。我再次将该提交标识为 git merge,并查看它的位置:以前是 *的提交,这是我们合并时返回的。

请注意,无论我们采用哪种合并方式,情况依然如此。

但是,至关重要的是我们进行实际的合并提交。如果使用不进行合并提交的 branch2,则不会得到这种图形。同样重要的是,合并后两个分支都不会“重新设置基础”,因为 git merge --squash通过复制提交起作用,而 git rebase基于提交标识和跟随父指针起作用。任何副本都是不同的提交,因此任何旧提交都不会指向新复制的提交。 (可以在合并点之后对提交进行基准调整(在这些图形中的右侧);不行的是复制左侧的提交。)

如果您不禁止 git merge执行“快进”操作,则 git merge也有可能跳过进行合并提交,而只是移动分支标签。在这种情况下,两个分支标签(您刚刚移动的一个和您要合并的一个)最终指向同一提交。一旦发生这种情况,除非将标签移回,否则无法“解缠”这两个分支。为防止 git merge快速执行此操作而不是实际合并,请使用 git merge

这是一个快进“合并”的示例(用引号表示,因为没有实际的合并)。与往常一样,我们从分支分支开始,但是当前分支 --no-ff上没有提交,而另一个分支 branch1上也没有提交:

...--o--*           <-- branch1
\
o--o--o <-- branch2


如果坐在 branch2上时运行 branch1(请注意缺少 git merge branch2),Git会注意到不需要进行实际合并。相反,它执行标签“快进”操作,将名称 --no-ff向前滑动,直到遇到 branch1上的尖端提交:

...--o--o
\
o--o--o <-- branch1, branch2


该图无处记录两个分支之间的任何“分离”,因此我们不妨弄清楚这些纠结:

...--o--o--o--o--o   <-- branch1, branch2


直到我们在 branch2上提交新的提交:

...--o--o--o--o--*     <-- branch1
\
o <-- branch2


这样做没有任何问题,但是请注意,现在无法断定我们“向上移动”到第一行的三个提交已合并。



1这对于常规 branch2git commit是正确的,但对于 git merge则不是。提交的“ amend”变体照常进行新提交,但不是将当前提交设置为新提交的父级,而是将当前提交的父级(尽可能多地设置为父级,甚至可能没有父级)全部)作为新提交者的父母。这样做的结果是将当前提交搁置一旁,看起来好像该提交已更改,而实际上旧的提交仍在存储库中。

2多于两个父母的情况称为“章鱼合并”,在这里我们可以忽略它。 (它对重复的成对合并没有任何作用。)

3在复杂图中,可能有不止一个这样的“第一点”。在这种情况下,所有最低共同祖先节点都是合并基础,对于Git, git commit --amend合并策略参数决定如何处理这种情况。 (当然,还有 -s strategy策略,它忽略了所有其他提交,只是完全绕开了三路合并代码。但是我在这里假设是正常的合并。)

关于git - Git merge 会影响“merge ”分支吗?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/40466290/

24 4 0
Copyright 2021 - 2024 cfsdn All Rights Reserved 蜀ICP备2022000587号
广告合作:1813099741@qq.com 6ren.com