众所周知,Git目前已经是分布式版本控制领域的翘楚,围绕着Git形成了完整的生态圈。学习Git,首先当然是学习Git的基本工作流。相比于SVN等传统版本控制系统来说,Git是专为分布式版本控制而生的强大工具。使用Git时常用的命令有pull、commit、push等,貌似很简单。不过,有时你会遇到合并冲突的情况,Git这时会将冲突标记出来,需要你手工来解决。有时,你会不小心将代码提交到错误的分支上,并且又推送到了远程 仓库。还有些时候,你需要切换到不同的分支,但Git却不让你这么做,因为还有未保存的修改。如果需要通过另一个分支的提交来为代码打补丁该怎么做呢?本 文就将介绍12个Git高级命令,合理使用这些命令可以大大提升应用Git的效率。
1. 使用rebase而非merge来拉取上游修改
分支合并会被记录为一次合并提交,这种做法是很有意义的。比如说,可以通过这种方式来标识一个新特性被合并到了发布分支中。不过,当多个团队成员工 作在一个项目中并使用常规的git pull来同步分支时,提交时间线就会被不必要的合并提交所污染。更好的做法则是使用git rebase将一个feature分支变基到master分支:
$ git checkout feature $ git rebase master这么做会将整个feature分支移动到master分支的起点,它会合并master分支上所有新的提交。不过,相比于使用合并提交来说,变基会 通过在原来的分支中为每次提交创建全新提交来重写项目历史。变基的主要好处在于你会得到一个更加整洁的项目历史。此外,这里还有关于变基的陷阱的一些讨 论。
2. 在执行git rebase后解决合并冲突
正如能力越大责任就越大一样。在执行git rebase时,你可能会遇到合并冲突的情况。合并冲突表示两个提交修改了同一个文件的同一行,Git不知道该应用哪一个修改。这会导致如下所示的错误消息:
Git会为你提供3个选择来修复导致冲突的提交(fa39187):
可以运行git rebase –abort来完全取消变基。这么做会取消变基修改,并将分支置回到执行git rebase之前的状态。
可以运行git rebase –skip来完全忽略该提交。这样,有问题的提交所引入的变化就不会被添加到历史中。
可以使用与合并冲突相同的标准步骤来解决冲突。
3. 临时性保存修改
在工作进行中时,有些东西常常会处于凌乱的状态。如果这时需要切换到不同的分支该怎么办呢?Git是不允许你这么做的,因为还有尚未保存的修改。坦 率地说,你并不想将半成品提交上去,后面再来修改。这个问题的解决之道就是使用git stash命令。Stash会接收工作目录的当前状态(比如说,修改了的追踪文件与暂存区的修改等),并将其保存到未完成的修改栈中,这样后面随时可以再 来修改。可以通过如下命令来暂存你的工作:
$ git stash Saved working directory and index state WIP on feature: 3fc175f fix race condition HEAD is now at 3fc175f fix race condition现在,工作目录就是干净的了:
$ git status # On branch feature nothing to commit, working directory clean这时就可以安全地切换分支做别的事情了。不过不必担心,暂存的提交依旧还在:
$ git stash list stash@{0}: WIP on feature: 3fc175f fix race condition稍后,在回到feature分支后,你就可以取回所有暂存的变更了:
$ git stash pop On branch feature Changes not staged for commit: (use "git add ..." to update what will be committed) modified: index.html Dropped refs/stash@{0} (ac2321cc3a33ba712b8e50c99a99d3c20da9d6b8)关于暂存,还有其他一些选项可用,如下所示:
$ git stash save "describe it" # give the stash a name $ git stash clear # delete a stashed commit $ git stash save --keep-index # stash only unstaged files4. 克隆一个特定的远程分支
如果想要从远程仓库中克隆一个特定的分支该怎么做呢?通常你会使用git clone,不过这么做会将所有其他分支都一并克隆下来。一个便捷的方式是使用git remote add:
$ git init $ git remote add -t -f origin $ git checkout5. 将cherry-pick远程提交合并到自己的分支中