Git & GitHub 杂记:HEAD到底是个什么东西

一般情况下,在查看提交的历史与差异中就能看到HEAD,也可能看到别人用 git reset HEAD <filename> 来撤销刚刚某文件的暂存,但 HEAD 到底是什么呢?

head 是对提交的引用。在谈论提交时,我们不谈提交名,而是说 head 。
当在不同的提交之间切换时,我们需要一种方法——当前磁头(被检出的磁头)即HEAD——来告知知道我们在哪个head上:

dang@DFLubuntu:~/testproject$ git log --oneline
b5c33cc (HEAD -> master) 向b.txt添加测试内容
2ae6624 向a.txt添加测试内容
639471b 新增两个用于测试的文本文件以及一个说明文件
5a4052c 再次修改问候语
c56e23d 修改问候语
60ba7bc 第一次提交
dang@DFLubuntu:~/testproject$ git show HEAD
commit b5c33cc4e0db85fe9380a3b58814c337e644070e (HEAD, master)
Author: xiaolu2333 <2694977226@qq.com>
Date:   Mon Nov 15 22:39:24 2021 +0800

    向b.txt添加测试内容

diff --git a/b.txt b/b.txt
index e69de29..ba62923 100644
--- a/b.txt
+++ b/b.txt
@@ -0,0 +1 @@
+BBB
  • 当前提交就是最新提交。

这里就需要区别两个概念,当前提交最新提交

  • 没有其他分支且没有切换提交时,情况是这样:这里只有一个master主分支,HEAD 指向 master 告诉我们正工作在名为 master 的 head 上,而 master 始终引用最新的提交,所以说 head 就是对最新提交的引用并且当前提交就是最新提交:
    在这里插入图片描述
  • 切换提交的操作就会改变 HEAD 的指向,我们可以通过检出等操作将当前状态定位到之前的某个提交,这就使得当前提交不是最新提交。此时的HEAD状态被称为HEAD的分离态:
    在这里插入图片描述
  • 当我们在当前提交后又创建一次提交,新提交会已分支的形式扩展出去,此时当前提交就又是最新提交了:
    在这里插入图片描述
  • 如果又切换回master时,当前提交就变为b5c33cc,它始终被master引用,而最新提交5a4202d由于没有被谁引用,它最终会被当成垃圾回收处理,除非我们在它被回收前创建一个分支名或者标签名来引用它:
    在这里插入图片描述

当切换提交时:

dang@DFLubuntu:~/testproject$ git checkout 5a4052c
注意:正在切换到 '5a4052c'。

您正处于分离头指针状态。您可以查看、做试验性的修改及提交,并且您可以在切换
回一个分支时,丢弃在此状态下所做的提交而不对分支造成影响。

如果您想要通过创建分支来保留在此状态下所做的提交,您可以通过在 switch 命令
中添加参数 -c 来实现(现在或稍后)。例如:

  git switch -c <新分支名>

或者撤销此操作:

  git switch -

通过将配置变量 advice.detachedHead 设置为 false 来关闭此建议

HEAD 目前位于 5a4052c 再次修改问候语

# 已回到具体的历史中的提交的状态
dang@DFLubuntu:~/testproject$ git show HEAD
commit 5a4052cf13aef78e15d3ae0fb71057e0996b3bad (HEAD)
Author: xiaolu2333 <2694977226@qq.com>
Date:   Mon Nov 15 14:45:05 2021 +0800

    再次修改问候语

diff --git a/README.md b/README.md
index 7bcfe7c..acd3ef0 100644
--- a/README.md
+++ b/README.md
@@ -1 +1 @@
-TESTPROJECT
+WELCOME TO TESTPROJECT
diff --git a/test.py b/test.py
index 3b0b1ed..509056f 100644
--- a/test.py
+++ b/test.py
@@ -1,4 +1,4 @@
 from datetime import datetime
 
-print("What's the time?")
+print("Now: ")
 print(datetime.today())
dang@DFLubuntu:~/testproject$ git log --oneline
5a4052c (HEAD) 再次修改问候语
c56e23d 修改问候语
60ba7bc 第一次提交
  • checkout 5a4052c 后 HEAD 指向了 5a4052c 提交。

再来看一个相关的概念:父提交
在我们的所有提交中,当前的提交是 b5c33cc ,那么它的父提交就是 2ae6624,所以说 HEAD 是对当前提交的引用时,那么 HEAD^ 或者 master^ 就引用当前提交的父提交:
在这里插入图片描述
之所以执行git reset HEAD <filename> 能撤销刚刚某文件的暂存,实际上是因为filename文件只是被添加到了暂存区而尚未被提交,这就尚未改变 HEAD 引用的当前提交,reset 只不过是重置了当前提交中filename文件的相关操作,也就是取消将它暂存到暂存区这一操作,从而达到撤销该文件的暂存的目的。

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值