其实上一篇《开发中关于Git那些事》写的内容仅仅是Git的冰山一角,如果你认为Git就是简简单单的几行命令,那只能说明你还没有真正了解Git这个强大的内容寻址文件系统。这篇文章,还是接着介绍一些实用但是很少有人知晓的一些命令,好比说具有魔性的Git变基(git rebase)以及常用的GUI。

我之前询问过一些人,讨论到Git这块,他们当中有的直接使用GUI,说简单省事。其实,每一个GUI都有它的侧重点,并不是所有的GUI都适合用。我倒是建议大家使用命令行。何况有些功能GUI不一定支持,而且有时候一行命令的事,还要点来点去,也不省事。之前看到过一篇文章,是关于如何使用Vim编辑器的,对,大家平时开发习惯了IDE,爱上了IDE。但是好的程序员怎么会因为简单省事而放弃学习呢。这样说可能更好提现,学习任意一款IDE,你都需要耗时很久,但是如果你平时习惯了使用Vim编辑器,爱上用Vim编辑器写代码,那么任意一款集成Vim编辑器的IDE,一上来就会非常顺手。同样的道理,如果你了解了Git内部原理,平时习惯使用命令处理,那么给你任意一款GitGUI,相信你一看就会用,而且很快就上手。所以,学习顺序有时候很重要,基础扎实了,才不会被问题难倒,地基决定高度。

1.客户端配置


1.1 修改默认编辑器

默认使用Vim编辑器,当然可以使用core.editor修改

git config --global core.editor emacs

1.2 修改log分页

默认使用less,可以使用core.pager来设置为more或则其他,也可以使用空字符串,关闭分页,一次性加载所有内容

git config --global core.pager ''

1.3 Git 中的着色

使用到color.ui,默认auto,如果你不喜欢可以使用false关闭。

git config --global color.ui false

其实如果想具体到某些特定命令,都是有true、false 或 always可以设置的,比如以下

color.branch
color.diff
color.interactive
color.status

以上每个配置项都有子选项,它们可以被用来覆盖其父设置,以达到为输出的各个部分着色的目的。例如,为了让 diff 的输出信息以蓝色前景、黑色背景和粗体显示,你可以运行

git config --global color.diff.meta "blue black bold"

你能设置的颜色有:normal、black、red、green、yellow、blue、magenta、cyan 或 white。正如以 上例子设置的粗体属性,想要设置字体属性的话,可以选择包括:bold、dim、ul(下划线)、blink 、reverse(交换前景色和背景色)。

2.实用命令


git branch -v 该命令显示本地分支最后一次提交说明

* dev    cdc7241a fixbug
master f586f6b5 ****

如果需要显示本地和远程,加上-a即git branch -v -a

* dev                   cdc7241a fixbug
master f586f6b5 ****
remotes/origin/HEAD -> origin/master
remotes/origin/dev cdc7241a fixbug
remotes/origin/master f586f6b5 ****
remotes/origin/oldIm 97d131bb 2.5.1 封版

git branch -vv 除了具有git branch -v命令的作用,还可以显示出每一个分支正在跟踪哪个远程分支,以及本地分支与远程分支是否是领先、落后。同样,如果想看远程加上-a,也就是all(所有),反正我就是这么记忆的

* dev    6512ef90 [origin/dev: ahead 1] test
master 78b4b30a [origin/master] 171227122 2.12.2 封版

3.Git变基(Rebasing)


实用举例1


其实在Git当中整合两个分支的方式除了**merge**,还有一种方式,那就是**rebase**。如上图,现在要合并C3和C4,如果使用**merge**合并是这样子的。它会把两个分支的最新快照(C3 和 C4)以及二者最近的共同祖先(C2)进行三方合并,合并的结果是生成一个新的快照(并提交)。

但是如果使用**rebase**:你可以提取在 C4 中引入的补丁和修改,然后在 C3 的基础上再应用一次。在 Git 中,这种操作就叫做**变基**。你可以使用 rebase 命令将提交到某一分支上的所有修改都移至另一分支上,就好像“重新播放”一样。
执行步骤就是,首先切换的experiment分支`git checkout experiment`,然后运行`git rebase master`,此时准备“重演”,接下来就是看你要在哪个分支重演,就切换到哪个分支,这边在主分支重演,切换到主分支`git checkout master`,然后整合即可`git merge experiment`。其实此时的**merge**和之前的**merge**不一样,这边的**merge**只需要进行一次**fast-forward**,就是快速合并,head快速前进到C4'。
它的原理是首先找到这两个分支(即当前分支 experiment、变基操作的目标基底分支 master)的最近共同祖 先 C2,然后对比当前分支相对于该祖先的历次提交,提取相应的修改并存为临时文件,然后将当前分支指向目标基底C3, 最后以此将之前另存为临时文件的修改依序应用。
```git
git checkout experiment
git rebase master
First, rewinding head to replay your work on top of it...
Applying: added staged command
```

```git
git checkout master
git merge experiment
```

此时,C4' 指向的快照就和上面使用**merge**命令的例子中 C5 指向的快照一模一样了。这两种整合方法的最终结果没有任何区别,但是变基使得提交历史更加整洁。你在查看一个经过变基的分支的历史记录时会发现,尽管实际的开发工作是并行的,但它们看上去就像是先后串行的一样,提交历史是一条直线没有分叉。

实用举例2

直接看下图,现在我有这样的需求,就是将C8,C9提交到主分支,但是不要C3,你如何做?



其实办法总是有的,在前篇文章中,有讲到git stash命令,其实,我们可以在client分支找到C3的哈希值直接执行git reset 哈希值(C3) 然后把C8,C9的修改直接git stash 贮存起来,切换到master分支,来个git stash pop搞定。现在我们使用变基来操作,感受下变基的魔性。

git rebase --onto master server client

以上命令含义:取出 client 分支,找出处于 client 分支和 server 分支的共同祖先之后的修改,然后把它们在 master 分支上重演一遍。

现在可以快进合并 master 分支了。

git checkout master
git merge client

实用举例3

再举一个例子,也是关于git rebase --onto的使用

                                   H---I---J topicB
/
E---F---G topicA
/
A---B---C---D master git rebase --onto master topicA topicB H'--I'--J' topicB
/
| E---F---G topicA
|/
A---B---C---D master
This is useful when topicB does not depend on topicA.

这样的例子好多,感兴趣可以使用git rebase --help查看。

注意事项

这点一定要看,不要对在你的仓库外还有副本的分支执行变基。也就是说,一个人开发随便搞,多人开发有原则的搞。如果你不遵循这个原则,多人开发出现问题别来找我。

为什么呢?假如有个人在本地使用了merge合并分支后,push到了远程服务器,后来他感觉不爽,想通过变基处理,恰是这个时候你pull了服务器的代码,那就会出现问题。问题就是,以后看记录会出现相同的提交,本来张三想丢弃的东西被你保留了。如果想看详细举例,推荐查看Pro Git这本书中关于Git变基一节。

总之,只要是你的代码和你建立的分支,还没有执行push之前,随意搞,push后就不要再想着使用变基了,避免出问题。如果你更喜欢merge,喜欢看Git实际发生的事,那就使用merge吧。反之,你更喜欢流水线一样的记录,从前到后,没有一堆堆复杂的合并,那就用rebase。

4.GitGUI


十几款GUI,点开查看即可。

SourceTree

GitHub Desktop

TortoiseGit

GitUp

......

我比较喜欢GitUp,简洁些。但是我仍旧在使用命令行,就当为了给电脑省空间吧。

开发中关于Git那些事(续:Git变基)的更多相关文章

  1. 版本控制git之三-多人协作 变基 推送 拉取 删除远程分支

      版本控制git之三-多人协作 wangfeng7399已关注0人评论350人阅读2019-02-20 21:33:08   如果你想获得一份已经存在了的 Git 仓库的拷贝,比如说,你想为某个开源 ...

  2. git rebase 版本。。变基

    git rebase,顾名思义,就是重新定义(re)起点(base)的作用,即重新定义分支的版本库状态.要搞清楚这个东西,要先看看版本库状态切换的两种情况: 我们知道,在某个分支上,我们可以通过git ...

  3. Git教程(7)用合并还是变基?

    合并或变基前的样子:分支experiment与master两个分支都产生了提交. 图1. 未合并或变基前的样子 合并 原理: 找到两个分支的最末提交和最近的共同祖先,在执行git merge时所处的分 ...

  4. git变基、冲突解决

    参考git rebase 版本..变基 git冲突解决先fetch,pull,如果文件冲突,手动处理冲突文件,然后再fetch,pull,发现拉不下来,这时需要将文件改为已合并,然后提交文件 具体操作 ...

  5. 开发中关于Git那些事

    如果你想精通Git,直接到 Git官网 把这本ProGit掌握已足以Pro Git 此文主要介绍一切开发中常用的git命令和一些配置技巧(诸如git别名配置,log打印技巧,版本回退以及分支管理等). ...

  6. GIT在iOS开发中的使用

    前言 在iOS开发中,很多公司对项目的版本控制管理都使用了git,当然也有部分公司使用的是svn.当年我最初接触的是svn,觉得使用起来挺方便的,但是每次切分支都需要下载一份新的代码起来,这实在太麻烦 ...

  7. fir.im Weekly - iOS开发中的Git流程

    本期 fir.im Weekly 收集了微博上的热转资源,包含 Android.iOS 开发工具.源码等好用的轮子,还有一些 APP 设计的 Tips,希望对你有用. 精仿知乎日报 iOS 端 @我偏 ...

  8. 团队项目开发中,常见的版本控制有svn,git

    团队项目开发中,常见的版本控制有svn,git

  9. 【搭建开发环境】在 Windows XP 中参与开源项目,搭建 git 和 cygwin 开发环境

    引言 只有一台 Windows XP 家用机,却想在诸如 Git@OSC 之类的开源社区参与开发,本文提供一个入门级的开发环境搭建指引. 涉及工具:Eclipse,EGit,Cygwin. 欢迎来到 ...

随机推荐

  1. Python数据分析中 DataFrame axis=0(0轴)与axis=1(1轴)的理解

    python中的axis究竟是如何定义的呢?他们究竟代表是DataFrame的行还是列? 直接上代码people=DataFrame(np.random.randn(5,5), columns=['a ...

  2. Python函数篇(二)之递归函数、匿名函数及高阶函数

    1.全局变量和局部变量 一般定义在程序的最开始的变量称为函数变量,在子程序中定义的变量称为局部变量,可以简单的理解为,无缩进的为全局变量,有缩进的是局部变量,全局变量的作用域是整个程序,而局部变量的作 ...

  3. linux grep 从入门到精通

    linux grep 从入门到精通 一.初级 搜索日志 grep "186" catalina.out 在新输出日志中监听固定字符串 tail -f catalina.out | ...

  4. php代码在服务器中查看接值

    error_log("You messed up!", 3, "/var/tmp/my-errors.log");

  5. PHP 字符串转 bigint 型md5

    1 2 3 4 5 6 7 8 /**      * 字符串转bigint      * @return bigint(string)      */     public function md5( ...

  6. c# 初识WPF

    WPF,全名是Windows Presentation Foundation,是微软在.net3.0 WinFX中提出的.WPF是对Direct3D的托管封装,它的图形表现依赖于显卡.当然,作为一种更 ...

  7. vue2入门之vue-cli

    vue-cli vue在web前端可谓是大放异彩,尤其在国内与angular.react有三足鼎立之势.很多人想入门vue2而又苦于不知从何下手.因为vue2是以组件化开发的,最好要搭配webpack ...

  8. js+画曲线和圆 并限制圆的渲染范围

    通过三个点的坐标可确定一条双曲线. 公式: 1)y=ax^2+bx+c; 2) y=a(x-k)+h; 通过已知三点可确定a,b,c,h,k 2.通过圆心坐标(a,b)和半径r可确定一个圆,和已知的x ...

  9. C语言写单链表的创建、释放、追加(即总是在最后的位置增加节点)

    昨天周末给学妹讲了一些指针的知识,本来我对指针就是似懂非懂的状态,经过昨天一讲,我对指针的学习就更深刻了 果然给别人讲课也是学习的一个方法.加上最近复习数据结构,发现我的博客里没有链表的博文,所以趁这 ...

  10. Java开发小技巧(一)

    前言 相信许多程序员在看别人写的代码的时候,会有怀疑人生的感想,面对一堆天书一样的代码,很难摸清作者的思路,最后选择了重构,如果你认同上面这个作法,说明了两个问题:要么原来的开发者技术菜.要么你技术菜 ...