在理解原理之前,我们应该知道git使用流程。git有三个区域,分别是工作区域(Working Tree)、暂存区域(index/stage)、已提交区域(Repository),文件在这三个区域中也有着不同的状态
git文件状态
git文件状态分为四种 Untracked(未跟踪)、staged(已暂存)、modified(已修改)、committed(已提交)

Untracked状态git status显示

modified状态在工作区域和暂存区域时分别为不同表示
在工作区域时,状态为Changes not staged for commit

在暂存区域时,状态为Changes to be committed

git原理理解
git本质是一个内容寻址文件系统,所有提交的文件都是以文件对象的形式存储在.git/objects中
在git中有这几种文件对象:
tag:对应版本分支的tag
tree:对应文件目录
blob:对应每一个文件
commit:对应每一次提交,使用的链表,带有上一次提交的commit
.git目录结构如下:

当使用git add时git会将add的文件的文件内容生成一个以SHA-1哈希值作为文件内容的校验和的文件对象,哈希值前两位为子目录,后面28位作为文件名存储在子目录中,最终存储在.git/objects文件目录中。并且在暂存区中会记录这些文件对象的哈希值映射
当使用git commit时,git会根据暂存区中的哈希值映射的blob对象以及他们对应的路径生成tree对象,最终生成commit对象,并且将这些对象存储在.git/objects文件目录中。
实验演示
当前git目录下,有a.txt,b.txt文件内容相同并且文件状态都是Untracked


使用git add a.txt, git add b.txt命令之后,使用git ls-files --stage命令查看暂存区blob对象的哈希索引列表,然后在进入到.git/objects文件目录发现文件对象也已经存入到文件目录中,因为git是以文件内容生成SHA-1哈希值和文件名称无关,所以a.txt和b.txt都是使用的同一个文件
![]()

![]()
使用git commit -m 'new file'之后,接着进入到.git/objects文件目录发现tree对象和commit对象文件也已经存入到目录中
使用git log查看最后一次提交的commit id已经在4e中目录中存储了

![]()

使用git cat-file -p 4ee1bf88c39a533b4c9d1ad637a5f2afe816de0a可查看此commit对象中包含的tree对象和blob对象

接着进入到tree对象,可以发现我们刚刚commit的a.txt和b.txt
![]()
下面我们修改一下b.txt文件然后commit,查看git log找到commit id

然后使用git cat-file -p d938ddec31acbaaf291010452e2d750e8a7536d3 查看这个commit对象,发现他包含了一个parent对象,这个parent对象就是上一个commit,每个commit对象就是一个链表,其中包含了上一次提交的commit对象

总结
1、git add都会在.git/objects文件目录下生成blob文件对象文件,并且在暂存区记录着每一个blob文件对象的哈希索引,
git commit之后会根据暂存区中的哈希索引生成tree对象,最终会生成commit对象, commit对象包含了文件目录的tree对象和文件blob对象以及上一次提交的commit对象。每次提交都会生成这样一个commit对象,并且存储在.git/objects文件目录中。
2、当在当前分支创建一个分支时,也只是将.git/HEAD文件指向创建的分支,并且在.git\refs\heads中的创建分支分支文件指向了
当前分支的commit,并不会为每个分支存储对应的文件对象,每个分支的commit对象还是都会存储在.git/objects文件目录中,所以对于git来说创建分支基本是无消耗,相当快速的。
3、当暂存区某blob文件的哈希值和commit对象中对应的blob文件哈希值不同时,文件状态就会是Changes to be committed。
当工作区和暂存区某blob文件的哈希值不同时,文件状态就会是Changes not staged for commit。
本文详细介绍了Git的工作流程,包括文件在工作区域、暂存区域和已提交区域的状态变化,以及Git如何通过内容寻址文件系统进行版本控制。通过实验演示,深入理解Git在每次提交时如何生成blob、tree和commit对象。
1268

被折叠的 条评论
为什么被折叠?



