目录
引言
Git鼓励开发者使用分支来进行程序的开发。但是最终只会有一个版本发行出去,因此,我们需要将开发好的分支merge(即合并,以下统称merge)到我们的主分支上。
前面的文章《Git初学札记(四)————Git Push的常规操作与Pull冲突解决》中已经简单的提到过merge的操作,但是,Git的merge功能并不局限于此。(比如,当其他开发者格式化了代码,这个时候我们又该如何merge?这里就涉及到了Git的高级merge功能。不过博主还没有找到EGit的相关设置)
在Git中合并是相当容易的。Git使得多次合并另一个分支变得很容易,这意味着我们可以有一个始终保持最新的长期分支。经常解决小的冲突,比在一系列提交后解决一个大的冲突要好。
在发生比较棘手的冲突时,Git并不会尝试智能地自动解决它,Git的哲学是聪明的决定无歧义的合并方案。
开始Merge
如何开始merge工作呢?EGit为我们提供了三个可以触发merge工作的入口:
1、History视图
2、Team菜单
3、Git Repositories视图
这三个视图中都有merge操作的入口,不论哪种方式,Git都是认为将其他分支merge到当前分支上。所以在merge之前,请先切换到主线分支上(注意主线分支并不代表master分支,这是相对而言的,主线分支可以是任何分支,例如有两个分支 A 和 B,如果要将B merge 到 A 上,那么A就是主线分支,B就是支线分支)。
巧用Git Staging视图
EGit的Git Staging视图不仅只是在add index 和commit 时才会用到,当发生merge冲突时也会有大用处。
EGit的官方文档这样写道:
A merge can result in conflicts which require user action. This is the case when the content of files cannot be merged automatically. These conflicts are marked with a label decoration in the Staging View. Using the Staging View to find the files with conflicts in order to resolve them is handy since the Staging View shows only modified files so that you don't have to wade through all of your resources but only those which might need your attention for resolving the conflicts.
Staging视图可以为我们准确聚焦需要我们集中注意力解决冲突的文件上,而不是由我们自己去搜索全部的资源文件。
在这里,我们可以右键冲突文件,选择我们希望的merging操作:
我们可以直接打开文件,看到<<<<<<<======>>>>>>>标记之后的文件内容(如下图),手动去修改。
也可以通过Merge Tool中提供的一些工具来进行merge操作,或者干脆双击文件,EGit会直接打开文件比对视图。
放弃Merging
当然,如果我们养成良好的习惯,经常merge小的改变,我们也不会苦了自己。但是,如果我们遇到了很多冲突修改需要merge 却没有足够的时间完成这些合并工作,我们该如何退出这次merge操作?
通常,当我们配置merge选项的时候都会选择如下单选框:
这并不是一个常规意义上的单选框,因为第三项完全可以和前两项同时存在。当选择第三项的时候,发生冲突后,会立刻终止merge操作,而不是将冲突文件标记成<<<<<<======>>>>>>>的一个文件。这样,我们就可以试探性的去进行merge操作,而不是一发生冲突,就立刻要去合并。
但如果我们仍然选择上图所示的默认配置,当发生冲突后,我们如何才能退出merging工作,或者暂时先不去完成冲突修改的合并工作呢?
这里有一个reset功能,了解一下:
当我们看到了如下图所示的一系列冲突文件而头大想去休息一下的时候,为了防止误操作,我们希望先退出合并编辑,一会再集中精力来解决它怎么办?
打开Team > Reset...
默认Hard选项即可,点击Reset按钮:
再次确认回退:
这样,我们就回退到了还没有点击merge按钮的样子:
这样,我们呆一会再来进行merge操作的时候就不会有任何问题了。
可能的Merge结果
merge可大致分为三种情况:Already-up-to-date ,Fast-forward ,Conflicting
下面是三种情况的merge结果会话框:
注意!!!Already-up-to-date代表两个分支的提交已经同步,而不是内容已经没有冲突!
如何解释这句话?假设,我们将B分支merge 到A上的时候发生了冲突。这个时候Git会将冲突内容全部写入当前分支的冲突文件中,用<<<<<=====>>>>>标记出来,并且要求使用者完成编辑操作。
这个时候我们已经进入了一种“merging”的状态,Git默认使用者此刻正在解决冲突。是的,它是这么认为的,然而,不论我们有没有认真修改冲突文件中的内容,也不论有没有真正意义上的完成了两个文件的修改整合工作,在我们点击commit之后,Git即默认我们已经完成了merge工作,Git就会将两个分支的指针指向同一个commit,并且将当前的主线分支标记为Merged。
可就在这时,我们突然想起来刚刚有一个方法没有merge进来,当我们再去merge这两个分支时,就会出现Already-up-to-date的结果,它代表两个分支的提交版本已经是同步了。
所以这点要格外注意,在merging的时候要尽可能的确保已经完成了所有修改的合并。因为一旦提交,Git将不再会认为这两个分支是有冲突的了。
综上,就是关于EGit在merge的时候涉及到的一些常规操作和一些基本视图。如有疑问,欢迎文末留言。
参考:《EGit/User Guide》