Git合并-同时合并2个分支会发生什么 [英] Git Merging - what happens to 2 branches being merged at same time

查看:1051
本文介绍了Git合并-同时合并2个分支会发生什么的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我对git的合并尚不清楚,我想正确理解。

I have an unclear understanding about merging on git, which I would like to understand correctly.

比方说,我在master分支上有一个文件F,已经是100 LOC。我从master创建一个分支A,然后写50 LOC,从第101行到第150行开始。我创建一个合并请求以将分支A合并到主服务器。因此,如果分支A将被合并,则master上的文件F将具有150 LOC

Let's say, I have a file F on master branch, which has already 100 LOC. I create a branch A from master, and I write 50 LOC, starts from line 101th to line 150th. I create a merge request to merge branch A to master. So if branch A will be merged, then file F on master will have 150 LOC

让我们假设分支A尚未合并到master上,仍在等待。然后我从master创建一个新的分支B。我还写了50条LOC,也是从第101行到第150行(因为分支A尚未合并)。而且我还为分支B创建了一个MR

Let's assume branch A isn't merged to master yet, still waiting. And I create a new branch B from master. I also write 50 LOC, starts also from line 101th to 150th (because branch A isn't merged yet). And I also create a MR for branch B

如果2个人检查2个MR,会发生什么情况,

What will happen, if 2 people review 2 MRs, and:


  1. 它们同时合并2个MR? master是否会发生冲突,因为两个分支都希望合并到第101行到第150行?

  1. They merge 2 MRs at the same time? Will master have a conflict, because both branches want to be merged into line 101th to 150th?

如果分支A首先合并,则意味着master已经具有150 LOC ,但分支B仍从第101行到第150行开始,因为它是在主行仍具有100 LOC时从主节点创建的。 B合并时还会有冲突吗?还是Git如何处理这些问题?

If branch A is merged first, means master already has 150 LOC, but branch B still starts from line 101th to 150th, because it was created from master when it still had 100 LOC. Will there be also a conflict when B is merged? Or how does Git handle these?

预先感谢(我不是巨魔,只是想弄清楚东西,以防有人举报这个问题)

Thanks in advance (I am not a troll, just want to figure out stuff, in case some people are going to flag this question)

推荐答案

我想澄清一下:冲突和合并策略是一个概念git本身。 OTOH是gitlab的概念(其他回购主机也有类似的概念),但对git本身毫无意义。最好通过谈论git来回答您的问题;因此,我们只需要知道合并请求就是一个工作流,可以通过该工作流在git中启动合并操作。因此,让我们将您的问题分为两个部分:

Something to clarify I think: conflicts and merge strategies are a concept of git itself. "Merge request", OTOH, is a concept of gitlab (and other repo hosts have similar concepts) but means nothing at all to git itself. Your question is best answered by talking about git; so we need only know that a merge request is one workflow by which a merge operation might be started in git. So let's take your question in two parts:

顺序合并

简短答案:可能会有冲突。

Short answer: there will probably be a conflict.

是否会发生冲突取决于合并策略。我的测试表明,通常会发生冲突,因为git看到第101-150行有替代更改。由于两组更改都已添加,因此我想您可以设想两组行都添加了无冲突-尽管尚不清楚它们的顺序您可以让git尝试使用 union 合并驱动程序来做到这一点;参见 http://kernel.org/pub/software/scm/git /docs/gitattributes.html

Whether there will be a conflict would depend on the merge strategy. My tests suggest there would typically be a conflict, as git sees alternative changes in lines 101 - 150. Since both sets of changes are adds, I guess you could conceive of both sets of lines being added without conflict - though it's unclear what order they would go in. You can make git try to do that using the union merge driver; see http://kernel.org/pub/software/scm/git/docs/gitattributes.html

您可以告诉git通过命令行参数以不同方式解析合并,但是由于这些指示将适用于整个提交-不只是设置此条件的一个文件-您通常不希望这样做。您可以使用 .gitattributes 影响git仅合并一个文件的方式,如果您可以提前知道何时该方法适用于整个文件。

You can tell git to resolve merges in different ways via command line arguments, but since those directions would apply to the entire commit - not just the one file where this condition is set up - you usually wouldn't want to. You could use .gitattributes to influence how git merges just the one file, if you can know in advance when that approach will be right for the (entire) file.

因此,有很多方法可以更改合并的行为-太多的细节在这里不知道具体的预期结果。但是,根据我的经验,通常使用默认的合并设置并解决冲突时通常效果很好。

So, there are a lot of options for how to change merge's behavior - too many to detail out here without knowing a specific desired result. But usually it works out well to use the default merge settings and resolve conflicts when they occur, in my experience anyway.

并发合并

实际上不可能在单个回购中同时进行两次合并。如果主机提供了某种直接在托管( origin )存储库上开始合并的方法-实际上我不知道有人这样做,但是出于争论的考虑-然后一个合并将必须首先完成,而另一个合并将合并的结果作为起点。因此,请参见答案的前一部分。

It is not really possible for two merges to occur "at the same time" within a single repo. If a host provides some way to start a merge on the hosted (origin) repo directly - which I don't actually know that anyone does, but for the sake of argument - then one merge would have to complete first, and the other would see the result of that merge as its starting point; so see the previous part of the answer for that.

可能发生的事情是,一个人可以在一个仓库中执行一个合并,而另一个人可以在一个仓库中执行另一个合并。第二个回购,那么当它们都尝试与远程同步时,可能会发生冲突。这就是它的外观:

What can happen is, one person can perform one merge on one repo, and another person can perform another merge on a second repo, and then there can be conflicts when they both try to sync up with the remote. And here's how that might look:

(请注意,在整个示例中,我假设 true合并,即如果使用 no-ff 选项。合并图可能更简单,但如果允许快速合并,则冲突的结果将相同。)

(Note that throughout this example I'm assuming true merges -- i.e. what would happen if you use the no-ff option. The merge graphs might be simpler, but the results would be the same as far as conflicts go, if fast-forward merges were allowed.)

因此回购始于

            B <--(branch_B)
           /
x -- x -- O <--(master)
           \
            A <--(branch_A)

所有提交都包含一个文件。在 O 中,该文件有100行。 A B 分别在文件末尾添加50行。

All commits contain a single file. In O that file has 100 lines. A and B each add 50 new lines to the end of the file.

现在,Alice合并了 branch_A ,而Bob合并了 branch_B ,每个都在其本地存储库中。因此,爱丽丝(Alice)有

Now Alice merges branch_A, and Bob merges branch_B, each in their local repo. So Alice has

            B <--(branch_B)
           /
x -- x -- O -- MA <--(master)
           \  /
            A
            ^-(branch_A)

和Bob有

            v-(branch_B)
            B
           /  \
x -- x -- O -- MB <--(master)
           \       
            A <--(branch_A)

要分享他们的作品,他们将各自尝试 push 来源;就像 merge s一样,即使它们试图在同一时刻开始推动,一个也将在另一个开始之前先完成。

To share their work, they will each try to push to origin; and just as with merges, one will complete first before the other starts even if they try to start pushing at exactly the same moment.

因此,爱丽丝得到了支持,并且起源已更新为看起来像她的本地人。当Bob尝试推动时,由于他的 master 上的 master 之后而出现错误。 origin (或者,可以说, origin / master 在更新后,假设使用典型映射)。

So Alice gets her push in, and origin is updated to look just like her local. When Bob tries to push, he gets an error because his master is behind the master on origin (or, we could say, behind origin/master once it's been updated, assuming typical mappings).

因此Bob必须<< c $ c> pull (或 fetch merge ),然后他就可以推送。为了最清楚地说明,我们假设他 fetch es。现在他有

So Bob has to pull (or fetch and merge) before he can push. To illustrate most clearly, let's suppose he fetches. Now he has

       v-(branch_B)
            B
           /  \
x -- x -- O -- MB <--(master)
          |\
          | MA <--(origin/master)
          |/
          A <--(branch_A)

并完成 pull 的效果,他需要将 origin / master 合并到 master -因此,即使是这种情况,也可以归结为首先介绍的顺序合并方案。实际上,如果您使用快进合并来跟踪同一场景,那么很明显,如果所有事情都是由一个用户在一个存储库中完成的,则此处需要的第二次合并与第二次合并完全相同。

and to complete the effect of a pull, he needs to merge origin/master into master - so even this case boils down to the "sequential merge" scenario covered first. In fact, if you trace the same scenario using fast-forward merges, it will be clear that the "2nd merge" needed here is exactly the same as the "2nd merge" if everything were done by one user in one repo.

这篇关于Git合并-同时合并2个分支会发生什么的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆