【原】Git 使用方法和原理(1)

git和其他的版本控制系统有很多差异, 其概念的命令都具有很强的混淆效果, 但是无奈速度快被大面积推广使用。。

pro git这本书介绍git的时候说要学好git先要把以前用的版本控制概念忘掉, 以避免混淆, 这个说的太好了。。同时书中也多次提到某个命令有点怪。。。可见开发git的都是一群怪人, 但同时git的版本推进过程中, 命令改动较大, 说明这群怪人也意识到这些命令太恶心了, 正在改进。

先从git记录版本的方式说起, git不同于最传统的版本控制系统, 它使用的是文件快照的方式, 而不是增量的方式。在版本库分布上, 有别于传统的只有服务器有完整的版本库的方式, git在每一台客户机上都有一套完整的版本库。

既然git是用快照的方式保存文件版本历史的, 那么具体是如何保存的呢?我们先新建一个版本库:

git init

创建好后打开目录中的.git文件夹, 发现这个目录中有个HEAD文件, 问什么叫HEAD呢?这是因为git使用类似链表的方式进行文件版本历史的索引,HEAD指向当前所在的分支的最后一次快照, 打开这个文件发现里面指向ref: refs/heads/master, 打开此目录发现里面并没有master这个文件, 这是因为我们还没有对版本库进行过操作, 也就没有快照, 我们先新建一个文件:

nano 1.txt

然后对其修改保存后, 将其添加到版本追踪:

git add 1.txt

此时对文件的添加操作就进入了操作缓存, 注意, 此时git还未将此操作进行提交, 只是进行了缓存, 执行下面的命令提交:

git commit

然后我们发现git创建了master这个文件, 打开master我们可以看到这次提交的一个唯一编号, 一个sha1值,这次提交的信息又指向一个文件记录文件目录结构的文件, 记录文件目录结构的文件又指向一个一个记录文件快照的文件, 这里引用pro git中的一个图:

这些文件全都放在object目录中, 以文件名称前两位分目录存储。

我们发现HEAD中记录的是master这个文件, 而我们知道git中默认的分支是master, 那么我们可以想象HEAD中记录的是当前所在branch的名称, 如果我们新建分支并将当前分支切换到新建的分支, 那么HEAD中的内容是不是应该有所变化呢?新建分支:

git branch testing

切换到新建的分支

git checkout testing

我们再来看HEAD文件, 果然, 其中的内容变成了ref: refs/heads/testing, 这时我们打开这个文件查看, 发现其中的内容和master中相同, 这说明git中分支指向的其实就是一次提交, 即一次快照。再来看一张pro git中的图:

在图中我们又发现每一次提交都指向上一次提交, 那么这个又是从哪记录的呢?在log目录中, 这里有HEAD指针的移动记录, 有各个分支的提交记录, git正是通过这样的链表结构来进行历史回溯的。

此条目发表在 Linux编程 分类目录,贴了 标签。将固定链接加入收藏夹。

发表评论

电子邮件地址不会被公开。 必填项已用*标注

您可以使用这些HTML标签和属性: <a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>