最近在学习git,对git也有了新的认识,写一些总结,文章基本总结于 Pro Gitcss
其余git相关文章:html
git学习系列(一)---- git的基础知识
git学习系列(二)---- git的分支git
本章主要介绍分支的合并与变基,分支的基础知识在上一章已经讲述过了。vim
注:图片中的箭头方向指向的是上一次提交(父对象),因此实际的提交顺序是从左往右。segmentfault
首先咱们来构建一个工做流程学习
1.首先,咱们假设你正在你的项目上工做,而且已经有一些提交spa
2.这个时候你须要开发一个新功能,你建立分支issue53并切换至他指针
git checkout -b iss53
3.你修改了一些东西,并作了提交(commit)code
vim index.html git commit -a -m 'added a new footer [issue 53]'
4.这时候你发现有个线上问题须要你紧急处理,因此你先切回master,并新建一个紧急分支hotfix,在hotfix上进行了修改htm
git checkout master git checkout -b hotfix vim index.html git commit -a -m 'fixed the broken email address'
5.问题已经解决,这个时候须要合并到master上线
git checkout master git merge hotfix
在合并的时候,你应该注意到了"快进(fast-forward)"这个词。 因为当前 master 分支所指向的提交是你当前提交(有关hotfix 的提交)的直接上游,因此 git 只是简单的将指针向前移动。
换句话说,当你试图合并两个分支时,若是顺着一个分支走下去可以到达另外一个分支,那么 git在合并二者的时候,只会简单的将指针向前推动(指针右移),由于这种状况下的合并操做没有须要解决的分歧——这就叫作“快进(fast-forward)”。
6.这个时候你能够返回issue53分支继续你的工做
git checkout iss53 vim index.html git commit -a -m 'finished'
你在 hotfix 分支上所作的工做并无包含到 iss53 分支中。 若是你须要拉取 hotfix 所作的修改,你可使用 git merge master 命令将 master 分支合并入 iss53 分支,或者你也能够等到 iss53 分支完成其使命,再将其合并回 master 分支。
7.issue53工做已经完成,你想要合并到master上
git checkout master git merge iss53
这和你以前合并 hotfix 分支的时候看起来有一点不同。 在这种状况下,你的开发历史从一个更早的地方开始分叉开来(diverged)。
由于,master 分支所在提交并非 iss53 分支所在提交的直接祖先,git 不得不作一些额外的工做。
出现这种状况的时候,git 会使用两个分支的末端所指的快照(C4 和 C5)以及这两个分支的工做祖先(C2),作一个简单的三方合并。
和以前将分支指针向前推动所不一样的是,git 将这次三方合并的结果作了一个新的快照而且自动建立一个新的提交指向它。这个被称做一次合并提交
8.遇到冲突时的解决方案
上述的操做是在没有冲突的状况下进行的,git会自动为你合并,并生成一个新的快照。然而当两个不一样的分支对同一文件作了不一样的修改,git就无能为力了,此时 git 作了合并,可是没有自动地建立一个新的合并提交,须要你本身去解决合并后的冲突,生成新的commit,而后再提交就能够了。
git merge iss53 Auto-merging index.html CONFLICT (content): Merge conflict in index.html Automatic merge failed; fix conflicts and then commit the result.
查看已合并分支与未合并分支
git branch --merged git branch --no-merged
在 git 中整合来自不一样分支的修改主要有两种方法:merge 以及 rebase
请回顾以前在 分支的合并 中的一个例子,你会看到开发任务分叉到两个不一样分支,又各自提交了更新。
你能够提取在 C4 中引入的补丁和修改,而后在 C3 的基础上应用一次。 在 Git 中,这种操做就叫作 变基。 你可使用 rebase 命令将提交到某一分支上的全部修改都移至另外一分支上,就好像“从新播放”同样。
git checkout experiment git rebase master
原理
1.首先找到这两个分支(即当前分支 experiment、变基操做的目标基底分支 master)的最近共同祖先 C2
2.对比当前分支相对于该祖先的历次提交,提取相应的修改并存为临时文件
3.而后将当前分支指向目标基底 C3
4.最后以此将以前另存为临时文件的修改依序应用
如今回到 master 分支,进行一次快进合并。
git checkout master git merge experiment
此时,C4' 指向的快照就和上面使用 merge 命令的例子中 C5 指向的快照如出一辙了。
这两种整合方法的最终结果没有任何区别,可是变基使得提交历史更加整洁。
你在查看一个通过变基的分支的历史记录时会发现,尽管实际的开发工做是并行的,但它们看上去就像是串行的同样,提交历史是一条直线没有分叉
假如在rebase时遇到冲突了该怎么解决
git自己会给出你下一步的提示,这时候你只须要打开冲突的文件,解决完冲突以后
git add . git rebase --contine
注:合并与变基虽然操做过程有差别,但最终你指向的快照是相同的
解决冲突时,新的修改会存储在补丁当中,即C4‘
原本还想着写一下变基可能会带来的风险与问题,可是本篇的篇幅已经有点长了,那就放在下一章讲述吧