git区域与对象

news2024/10/6 1:44:46

大纲

工作区(workspace directory):本机的代码项目,是一种沙箱环境

暂存区(stage index):工作区在程序员写程序的过程中会发生无数次改动,git不可能记录每一次的改动,这些改动的过程在暂存区负责记录,暂存区会将最终的状态随着程序员的提交而提交到版本库

版本库(history):保存由程序员从暂存区提交上来的程序

在这里插入图片描述
工作区 => 暂存区操作指令:git add files 其实做了两件事:
①将本地文件的时间戳、长度,当前文档对象的id等信息保存到一个树形目录index中去,即平时说的暂存区
②将本地文件的内容做快照并保存到Git 的对象库,实际上就是一个包含文件索引的目录树,像是一个虚拟的工作区。在这个虚拟工作区的目录树中,记录了文件名、文件id等状态信息存储在index中,文件的内容并不存储其中,而是保存在 Git 对象库(.git/objects)中,文件索引建立了文件和对象库中对象实体之间的对应。

总之:当对工作区修改(或新增)的文件执行 “git add” 命令时,暂存区的目录树被更新,同时工作区修改(或新增)的文件内容被写入到对象库中的一个新的对象中,而该对象的ID 被记录在暂存区的文件索引中

补充:git ls-files -s 查看暂存区的内容,暂存区的内容不会自动变化,即使是提交到了版本库也不会影响暂存区的内容,只能通过以下指令进行清除

2 暂存区 => 工作区 git reset – files
用来撤销最后一次git add files(因为每git add file一次,暂存区的文件都会被更改一次),你也可以用git reset 撤销所有暂存区域文件。

3 暂存区 => 版本库 git commit -m “注释内容”
当执行提交操作时,暂存区的目录树写到版本库(对象库)中,master 分支会做相应的更新。即 master 指向的目录树就是提交时暂存区的目录树

工作区和版本控制区

我们采用更细粒度的划分探究底层原理
① echo “xxx” | git hash-object --w -stdin 将xxx的内容写入objects(版本区)内,路径:前两个字母作为objects中的目录,后面的字母组成文件名

执行第一行命令时向git中存储“test content”,第二行返回生成的内容(第一个是只生成内容的哈希码,第二个是生成且保存到文件objects中去)在这里插入图片描述
随后我们发现,.git/object下会生成相应文件夹,这也代表写入成功;其中文件夹名是上面第二行返回哈希码的前两个字母,文件名是后面的哈希吗;通过文件名(哈希码)可以获取文件的内容和类型,所以git对象是键(hash)值(blob类型的数据)对类型的数据
在这里插入图片描述
git cat-file -p 哈希码:如果是写入到objects中的哈希码就能通过该命令读取到文本值:test content
在这里插入图片描述
② git hash-object --w ./test.txt 将当前命令行目录下的test.text文件写入objects中
git cat-file -p 文件哈希码:这个命令可以读出原文件的值
在这里插入图片描述
经查看写入文件结果就是文件本身的内容 ,如果我们此时通过vim修改并保存了这个文件objects的内容还不会变化,我们必须再次执行写入命令将修改后的test文件再次写入,原有的内容会被覆盖同时新内容也会被添加进去;
在这里插入图片描述
以上操作是片面的,有以下不足:1 无法记住文件所对应的每一个版本极其哈希值; 2我们只是保存了文件的内容但没有保存文件的名字; 3当前操作都是在本地数据库进行的(当前操作是直接由工作区 => 版本库),不涉及暂存区;综上所述,git对象由于无法明确的描述每个项目的信息(项目名,版本,文件内容),且本质上一个git对象代表一个唯一的文件(初始化写入两个文件代表两个git对象,我们分别对这两个文件修改了2次和3次并重写写入这个文件到objects达到更新效果,最后git对象数目为2+3=5个,由此可证以上结论),git对象无法作为项目快照,git只是一个文件对象版本

树对象

树对象可以解决文件名保存问题,允许我们将多个文件组织在一起,Git用了类似UNIX操作系统的方式存储内容,所有的内容均以树对象(tree)和数据对象(git)的方式进行存储,其中tree对应了目录下,git代表了数据项,一个数对象代表了一条或多条记录,每条记录其实就是一个指向git或tree子树的指针;我们可以通过update-index,read-tree和write-tree等命令构造树对象并将其塞到缓冲区

最开始暂存区也是存在的,只不过为空,git ls-file -s可以查看暂存区内容(最初里面的内容为空;

创建缓存区并向其添加文件的过程:
以上操作 1 ①生成文件test.txt并将其存入git对象中返回一个键(哈希值)值(文件本身)对,将该文件作为第一个(该文件代表一个项目,注意为②update-index命令生成的是暂存区而不是具体的文件,为test文件的首个版本创建一个暂存区,第一次向暂存区添加内容用add③100644代表一个普通文件 100755代表一个可执行文件 12000代表一个符号链接③通过)④cacheinfo代表着去数据库取对象,如果是在当前文件夹下取对象就不用写任何东西⑤去查看objects下生成的文件,发现test.txt已被加入暂存区⑤git ls-files -s是查看暂存区内容,可见test.text被加入了暂存区⑥查看objects中去查看,只有一个存储test.txt的git对象,也就是说暂存区的数据见名知意,只是暂存存储,不会主动进行提交
在这里插入图片描述
2 git write -tree是生成暂存区的对象tree同时提交到版本库中(存储到objects下),我们可以不断的向暂存区进行增删改直到自己满意再进行提交,git对象代表文件的一次次版本,tree对象代表项目的一次次版本,这就是暂存区的作用,因为objects本来就有一个关于test.txt的git对象,后来又接收了一个从缓存区提交上来的test.txt的tree对象,所以有两个对象类型;也就是我们可以不断的在工作区修修补补然后不断的提交到暂存区,最终将确定下来的版本从暂存区提交到版本库,总之git对象代表文件的一次次版,tree对象代表项目的一次次版本
在这里插入图片描述
经实验,暂存区提交后里面的数据并不会消失,但如果再次从暂存区进行提交也不会再生成新的树对象,只有在工作区项目发送变化且执行"git add xxx"后暂存区数据更新为最新一次的提交

先将new.txt文件写入一个git ,查看objects数据库
在这里插入图片描述
修改test文件后需要在将test写入git,继续查看objects数据库有四个对象在这里插入图片描述
分析objects中的四个对象
在这里插入图片描述

此时在再更新一下暂存区,更新test.txt为最新版本,可见工作区与暂存区一致,其中的结果永远是工作区最新的结果

在暂存区首次添加(add)new.text的版本,缓冲区多了一个new.text的git对象;此时暂存区的状态跟工作区是一致的,是可以代表项目的调用版本 ,此时暂存区中已经有两个对象了,但数据库(版本库)中依然只有一个,最后我们用git write-tree来将暂存区最新状态提交到版本库中
在这里插入图片描述
最后数据库中有五个对象,其中最后生成的一个是workspace第二个版本的tree对象
在这里插入图片描述
其中9d/…是第工作区WorkSpace二个版本的对象,该版本有test.txt的v2和new.txt的v1;
在这里插入图片描述
ead-tree:可以把树对象读入到暂存区,我们把第一颗树对象读入进来(暂存区)
在这里插入图片描述
我们在暂存区将其生成树对象读入到控制区(正常情况下实际操作中不存在这种情况)

在这里插入图片描述
此时控制区的这个树对象的总结构为:
在这里插入图片描述
在这里插入图片描述

提交对象

以上tree对象依然不是全面的步骤,虽然可以获取到项目的文件,文件数目,文件名等重要信息但我们无法得知这几个版本分别干了那些事;也就是如果能在tree对象上直白的加上注释就好了

提交对象commit的本质是对树对象tree进行封装(只需要传入前8位的tree对象的hash值即可进行封装),添加一些必要的信息如父对象,作者的name和email,被封装为该commit对象的tree对象,封装tree对象时添加的注释内容

注意,第一次提交产生的commit对象不存在父对象,是跟节点,但随后产生的树对象必须有父对象也父对象是它的上一个提交对象

这就是commit的重要属性:链式意味着commit的信息是连成一串的;commit-tree不仅会生成提交对象还会连带与它相应的tree对象提交到本地数据库
总之,项目快照的本质是一个tree对象,项目完整版本本质就是一个提交对象commit,而版本穿梭的本质就是利用了提交对象链式存储的特点;
在这里插入图片描述

总结:add add是将git对象直接读入到控制区备份(git对象的生成是增量式的而非覆盖式的),再在从控制区到暂存区,这样用户进行了多次操作涉及到了多个git,直到用户满意进行提交时才形成一个完整的版本tree对象,再将tree通过指令提交到到版本库,但此时的tree对象内容过于空白让人懵逼,于是我们再次拿出加入一些必要的信息将tree封装为commit对象 ,然后通过指令提交到控制区

一个commit对象对应于一个tree对象,真正表示一个版本;

一个tree对象对应多个git对象,对应一个版本快照故对应多个文件;

一个git对象代表一个文件,项目第一次提交时,项目有多少文件就生成多少个git对象,每次修改后再次提交时生成的git对象数量与项目中被修改的文件数目一致;

Git的特点:1 多数操作均为本地环境下完成; 2多数操作以添加为主; 3 git每次存储的是都是版本快照而非差异存储 ;4 git时刻保持数据的完整性; 5 git数据有三种状态①以修改(modified)②已暂存(staged)③已提交(committed)

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1514793.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

springboot与elasticsearch-7.16.2的基础CRUD使用——入门向

highlight: an-old-hope 基于elasticsearch-7.16.2 ,使用的是旧版的高级客户端 restHighLevelClient springboot版本2.6.13 项目原代码地址 https://gitee.com/kenwm/es7demo.git 参考博客 1、SpringBoot集成ElasticSearch,实现模糊查询,批…

学python新手如何安装pycharm;python小白如何安装pycharm

首先找到官网: Download PyCharm: The Python IDE for data science and web development by JetBrains 打开后选择下载,下图标红部分 点击exe程序,点击下一步! 选择安装路径,下一步 弹出界面全选 选择默认 然后直接…

Spring核心接口:BeanFactory接口

一图胜千言 BeanFactory 属性&方法解析 点击展开注意:以上代码仅供参考,可能存在不完整或不准确的情况。 public interface BeanFactory {// 根据Bean名称返回Bean实例。// 如果Bean不存在,则抛出NoSuchBeanDefinitionException异常。Obj…

华为机考:HJ43 迷宫问题

华为机考:HJ43 迷宫问题 描述 DFS 从迷宫入口开始进行dfs搜索,每次进入一个点,将其加入临时路径数组中,把该位改成0表示不能进入,然后依次搜索该位下、右、上、左四个方向的点,如果搜索的这个点可以进入则…

【机器学习智能硬件开发全解】(二)—— 政安晨:嵌入式系统基本素养【处理器原理】

嵌入式系统的基本素养包括以下几个方面: 硬件知识:嵌入式系统通常由硬件和软件组成,了解和熟悉硬件的基本知识,包括微处理器、存储器、外设等,并了解它们的工作原理和特性。 软件编程:熟悉至少一种编程语言…

STM32模拟I2C控制TM1650数码管显示电压电流

模拟I2C控制TM1650数码管显示电压电流 数码管的逻辑TM1650 原理模拟I2C的实现TM1650驱动电压电流显示 数码管的逻辑 通过数码管来表示字符。 数码管的abcdefg和dp分别对应这发送过去的8位数据位比如0x3F -> 0011 1111 表示0字符。 如果要加上小数点则在最高位加一&#xf…

同步整流芯片 支持12V降5V 24V降5V 24V降12V 降压芯片 H4122

惠海H4122降压恒压芯片的工作原理: 主要是通过内部电路和算法来控制和调节输出电压,使其保持恒定。 输入电压:芯片接收一个较高的输入电压,如12V、24V或36V。 开关电源转换器:芯片内部通常包含一个或多个开关电源转…

【python pyinstaller库】pyinstaller介绍、安装、以及相关重点知识

PyInstaller是一个在Windows、GNU/Linux、macOS等平台下将Python程序冻结(打包)为独立可执行文件的工具, 用于在未安装Python的平台上执行Python编写的应用程序。 相比类似工具,它的主要优点是 PyInstaller 与 Python 3.7-3.10 一起工作&…

StarRocks实战——云览科技存算分离实践

目录 背景 一、平台现状&痛点 1.1 使用组件多,维护成本高 1.2 链路冗长,数据时效性难以保证 1.3 服务稳定性不足 二、StarRocks 存算分离调研 2.1 性能对比 2.2 易用性 2.3 存储成本 三、StarRocks 存算分离实践 3.1 查询优化 3.1.1 物化…

SyntaxError: Unexpected end of JsON input J50N.parse....报错

const userInfoJSON.parse(uni.getStorageSync(userInfo))改成 const userInfouni.getStorageSync(userInfo)&& JSON.parse(uni.getStorageSync(userInfo)) //不报错

ChatGPT国内能用吗?中国用户怎么才能使用ChatGPT?

与ChatGPT类似的国内网站,他们都能提供和ChatGPT相似的能力,而且可以在国内直接使用。 点击直达方式 百科GPT官网:baikegpt.cn ChatGPT是基于GPT-3.5架构的语言模型的一个实例,由OpenAI开发。以下是ChatGPT的发展历史&#xff1…

深入理解Python中的面向对象编程(OOP)【第129篇—Scikit-learn的入门】

深入理解Python中的面向对象编程(OOP) 在Python编程领域中,面向对象编程(Object-Oriented Programming,简称OOP)是一种强大而灵活的编程范式,它允许开发者以对象为中心组织代码,使得…

Redis7.2.4分片集群搭建

Redis分片集群搭建 1.集群结构 分片集群需要的节点数量较多,这里我们搭建一个最小的分片集群,包含3个master节点,每个master包含一个slave节点,结构如下: 信息如下: IPPORT角色glnode036379slaveglnode0…

JavaEE:文件IO

硬盘 文件指的是硬盘/磁盘上的文件 ⚠硬盘 ≠ 磁盘 磁盘属于外存的一种;而软盘,硬盘(机械硬盘)这种属于用磁性介质来存储二进制数据 ssd硬盘(固态硬盘),内部完全是集成电路,和磁…

手写简易操作系统(七)--加载操作系统内核

前情提要 上一节中,我们开启了内存分页,这一节中,我们将加载内核,内核是用C语言写的,C语言编译完了是一段ELF可加载程序,所以我们需要学会解析ELF格式文件,并将内核加载到内存 一、ELF格式 程…

(黑马出品_高级篇_04)SpringCloud+RabbitMQ+Docker+Redis+搜索+分布式

(黑马出品_高级篇_04)SpringCloudRabbitMQDockerRedis搜索分布式 微服务技术——可靠性消息服务 今日目标服务异步通信-高级篇1.消息可靠性1.1.生产者消息确认1.1.1.修改配置1.1.2.定义Return回调1.1.3.定义ConfirmCallbac…

【LeetCode热题100】2. 两数相加(链表)

一.题目要求 给你两个 非空 的链表,表示两个非负的整数。它们每位数字都是按照 逆序 的方式存储的,并且每个节点只能存储 一位 数字。 请你将两个数相加,并以相同形式返回一个表示和的链表。 你可以假设除了数字 0 之外,这两个数…

论文阅读——RemoteCLIP

RemoteCLIP: A Vision Language Foundation Model for Remote Sensing 摘要——通用基础模型在人工智能领域变得越来越重要。虽然自监督学习(SSL)和掩蔽图像建模(MIM)在构建此类遥感基础模型方面取得了有希望的结果,但…

深度学习系列62:Agent入门

1 anget介绍和openai标准接口 agent的核心是其代理协同工作的能力。每个代理都有其特定的能力和角色,你需要定义代理之间的互动行为,即当一个代理从另一个代理收到消息时该如何回复。 agent目前大多使用openai标准接口调用LLM服务,说明如下。…

Java集合基础知识总结(绝对经典)

List接口继承了Collection接口,定义一个允许重复项的有序集合。该接口不但能够对列表的一部分进行处理,还添加了面向位置的操作。 实际上有两种list:一种是基本的ArrayList,其优点在于随机访问元素,另一种是更强大的L…