Git 应该在对本地主站进行更改后使用推送或合并到远程主站

  • 本文关键字:主站 合并 程主站 Git android git
  • 更新时间 :
  • 英文 :


我从git克隆了一个Android项目,并从master创建了一个名为devBranch的本地分支。

我在devBranch中做了很多更改,我也远程推送了它。

现在,一旦我完成了devBranch中的所有更改,我就将这些更改合并到主本地分支中。

现在我想将本地主站中的这些新更改推送到远程主站。

什么是合适的方法?我应该使用推送还是合并,为什么?

git pushgit merge进行比较不是很明智:

  • git push命令是关于将一些提交发送到负责其他仓库的其他 Git,以便其他仓库获得新的提交,然后要求其他 Git 调整该其他仓库中的某些分支和/或其他名称。

  • git merge命令很复杂,但当以典型方式之一使用时,是在您自己的存储库的当前分支中进行新提交。 此新提交通常是具有两个父级的合并提交,而不是具有一个父级的更常见的普通提交

现在,在某些情况下,git merge不会进行新的提交,而是执行快进操作。 快进操作是对分支名称的更改,以便存储在该名称中的新提交哈希 ID 标识其哈希 ID 以前存储在该名称中的提交的后代。 (这是一个非常多的行话,需要一点图论才能理解。 有关一个简单的示例,请参见下文。

git push命令还可用于发送任何新提交,但仍请求其他 Git 存储库对其分支名称之一进行更改。 此更改可以是快进操作,无论您的 Git 是否发送任何新提交。 实际上,如果分支名称更改是非快进操作,则git push命令需要--force--force-with-lease选项。

由于git mergegit push都可以进行这种快进行动,因此至少有一种情况两者具有一定的可比性。 但是,这种特殊情况的主要区别在于,git merge在您的存储库中执行快进,而git push在其他Git 存储库中执行快进。

可以说,底线很简单:

  • 如果需要进行合并提交,则必须在本地执行此操作。git push命令无法执行此操作。
  • 如果您不需要进行合并提交,请问问自己谁的分支名称需要哪种更新。 若要更新自己的分支名称,请在本地工作。 要更新其他一些 Git 存储库,请使用git push

请记住,存储库共享提交(通过哈希 ID),但有自己的私有分支名称。 你的名字不是别人的名字,也不需要以同样的方式使用——但人类就是人类,我们倾向于以同样的方式使用相同的名字,因为如果我叫你弗雷德,而你的同事叫你皮奥特,而你的名字实际上是拉胡尔,这太令人困惑了。

绘制快进的含义

为了理解 Git 的快进概念,让我们从分支名称包含提交哈希 ID 的事实开始,并且提交也包含提交哈希 ID。 每当某物持有提交哈希 ID 时,我们都会说该某物(无论它是什么)都指向该提交。 因此,提交指向另一个提交,分支名称指向提交。

任何给定提交的实际名称都是一些丑陋的大哈希ID,例如faefdd61ec7c7f6f3c8c9907891465ac9a2a1475。 这些太烦人了,无法输入,而且对于人类来说太棘手了,所以让我们使用大写字母绘制我们自己的 Git 提交图片段来代替每个提交。 在这里,我们连续三次提交,最后一个(最新的)提交H

... <-F <-G <-H

由于H最新的提交,我们将有一个分支名称指向它:

... <-F <-G <-H   <--master

同时,提交H本身实际上存储了早期提交G的原始(和真实)哈希 ID。 所以H指向G. 提交G反过来,将更早提交F的哈希 ID 存储在其中:G指向F。 这就是我们在这里绘制的内容。

任何提交的任何部分,一旦完成,就永远无法更改。 这意味着我们实际上不必将提交之间的内部向后箭头绘制为箭头:我们可以将它们绘制为连接线。 当我们开始添加更多提交时,这很有用H,使用另一个名称来查找它们:

...--F--G--H   <-- master

I--J   <-- dev

在这里,分支名称dev指向提交J,向后指向提交I,向后指向提交H,依此类推。 同时,名称master仍然指向现有的提交H

我们现在可以要求 Git "将名称向前滑动master"。 如果我们只向前推进一次提交,master最终会指向I,如下所示:

...--F--G--H--I   <-- master

J   <-- dev

请注意提交是如何没有改变的:我们只是将提交I高了一行,因为没有其他好方法可以在 StackOverflow 上绘制它们。 名称已更改,或者更准确地说,存储在名称中的master更改,因此master现在指向I

如果我们一直向前滑动master,我们会得到:

...--F--G--H

I--J   <-- dev, master

现在根本没有理由继续纠结:

...--H--I--J   <-- dev, master

够。

这个操作——移动主节点"前进"一个或多个提交——就是 Git 所说的快进,因为即使master现在指向IJ,我们可以通过从我们现在通过该名称找到的任何提交开始,向后工作到master之前的位置。它在提交HJ指向I指向H。 因此,提交H保留名为master的分支上。

但是,如果我们从这个开始呢:

...--F--G   <-- master

然后添加一个新名称dev也指向现有的提交G

...--F--G   <-- dev, master

然后在master上进行一个新的提交,以便它指向这个新的提交H,但随后签出分支dev并在dev上进行一个新提交,以便dev指向新的提交I? 我们现在将有:

H   <-- master
/
...--F--G

I   <-- dev

master(定位提交H),我们可以回到提交G,然后提交F,依此类推。 从dev(提交I)开始,我们可以回到GF等等。 但是这些连接提交的箭头完全是向后箭头。 我们不能从G"前进"到H. Git 的连接只指向方。 我们需要master名称,以便在返回之前找到提交H

如果我们强制 Git 将名称master移动到指向提交I,我们最终会得到:

H   ???
/
...--F--G

I   <-- dev, master

提交仍然存在,但我们无法找到它的哈希 ID。 提交H丢失:它仍然存在(一段时间),但除非我们迫使 Git 合理快速地恢复它,否则 Git 最终会完全删除它,因为它是不必要的。1这种强制名称动议,其中提交H丢失,是一种非快进

如果我们想加入提交HI,并保持在两者中完成的工作,我们需要使用git merge(或类似的东西)。


1在普通存储库中,Git 会留下痕迹,让我们至少再恢复 30 天。 在服务器上的裸存储库中,恢复时间要短得多。

适当的方法是执行git push

为什么?因为您有一个远程存储库,并且希望将当前工作状态保存到该远程存储库。遥控器只是帮助您保存不同的提交和当前工作状态。 这有两个好的目的:1. 您可以使用相同的遥控器与其他团队成员协作,2.即使没有本地计算机,您也可以在任何地方访问存储库。

git merge创建合并的两个分支的统一分支。如果您执行 git 合并,则远程上的文件将与本地计算机上的当前工作文件合并。git merge变得更加复杂,主要处理本地计算机上的文件

Udacity 有一个免费的关于 git 和 git hub 基础知识的好课程

相关内容

  • 没有找到相关文章

最新更新