git中的head到底是怎么工作的,十分钟就够了

2024-08-31 16:04

本文主要是介绍git中的head到底是怎么工作的,十分钟就够了,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!

git中的head到底是怎么工作的,十分钟就够了

  • 背景
  • HEAD 实际上是一些不同的东西
  • 文件 .git/HEAD
  • HEAD如同git show HEAD
  • 下一步:所有输出格式
    • git status:“在主分支上”或“HEAD 分离”
    • 分离 HEAD 状态
    • git log:(HEAD -> main)
    • 合并冲突:<<<<<<< HEAD很令人困惑
  • 关于术语一致性的一些想法
  • 就这样!

背景

一般上讲当说某个话题令人困惑而我认为它并不令人困惑时,原因是其中实际上存在一些我没有考虑到的隐藏复杂性。我发现这HEAD 实际上比我想象的要复杂一些!

HEAD 实际上是一些不同的东西

在与许多不同的人谈论之后HEAD,我意识到 HEAD实际上有几个不同的密切相关的含义:

1)文件 .git/HEAD
2)HEAD就像这样git show HEAD(git 称之为“修订参数”)
3)git 在各种命令HEAD的输出中使用的所有方法( <<<<<<<<<<HEAD、、、、等)(HEAD -> main)detached HEAD stateOn branch main
4)它们彼此之间极其密切相关,但我认为对于刚开始使用 git 的人来说,这种关系并不完全明显。

文件 .git/HEAD

Git 有一个非常重要的文件,叫做.git/HEAD。此文件的工作方式是,它包含以下内容之一:

1)分支的名称(如ref: refs/heads/main)
2)提交ID(例如96fa6899ea34697257e84865fefc56beb42d6390)
此文件决定了 Git 中的“当前分支”。例如,当你运行git status并看到以下内容时:
$ git status
On branch main

这意味着该文件 .git/HEAD 包含 ref: refs/heads/main

如果.git/HEAD 包含的是提交 ID 而不是分支,git 会将其称为“分离的 HEAD 状态”。我们稍后会讲到这一点。

(有时会说 HEAD 包含引用 的名称或提交 ID,但我很确定该引用必须是一个分支。从技术上讲,可以.git/HEAD 通过手动编辑来包含非分支的引用的名称.git/HEAD,但我不认为可以使用常规 git 命令来做到这一点。我很想知道是否有一种常规 git 命令方法可以使 .git/HEAD 成为非分支引用,如果是的话,为什么要这样做!)

HEAD如同git show HEAD

HEAD在 git 命令中引用提交 ID是很常见的,例如:
git diff HEAD
git rebase -i HEAD^^^^
git diff main..HEAD
git reset --hard HEAD@{2}

所有这些(HEAD、HEAD^^^、HEAD@{2})都称为“修订参数”。它们记录在man gitrevisions中,Git 会尝试将它们解析为提交 ID。

老实说,我以前从未听说过“修订参数”这个术语,但这个术语可以让你了解这个概念的文档

HEAD 的git show HEAD含义非常简单:它解析已检出的当前提交HEAD!Git以两种方式之一解析:

  1. 如果.git/HEAD包含分支名称,它将是该分支上的最新提交(例如通过从中读取.git/refs/heads/main)

    2)如果.git/HEAD包含提交 ID,则为该提交 ID

下一步:所有输出格式

现在我们已经讨论了文件.git/HEAD 和“修订参数” HEAD。我们剩下的就是 git在其输出中git show HEAD使用的各种方式。HEAD

git status:“在主分支上”或“HEAD 分离”

当运行时git status,第一行将始终看起来像以下两行之一:

on branch main。这意味着.git/HEAD包含一个分支。
HEAD detached at 90c81c72。这意味着.git/HEAD包含一个提交 ID。现在我来解释“HEAD detached”是什么意思。

分离 HEAD 状态

“HEAD 已分离”或“HEAD 分离状态”意味着您没有当前分支。

没有当前分支有点危险,因为如果你做了新的提交,这些提交将不会附加到任何分支 - 它们将被孤立!孤立提交是个问题,原因有 2 个:

1)提交更难找到(你不能跑去git log somebranch寻找它们)
2)孤立的提交最终将被 git 的垃圾收集删除

就我个人而言,我非常小心地避免在分离的 HEAD 状态下创建提交,尽管有些人更喜欢这样工作。但是,退出分离的 HEAD 状态非常容易,您可以:

1)返回分支 ( git checkout main)

2)在该提交处创建一个新分支(git checkout -b newbranch)

3)如果你处于分离 HEAD 状态,因为你正处于变基过程中,请完成或中止变基(git rebase --abort)

好的,回到其他 git 命令的HEAD输出!

git log:(HEAD -> main)

当您运行git log并查看第一行时,可能会看到以下 3 种情况之一:

commit 96fa6899ea (HEAD -> main)
commit 96fa6899ea (HEAD, main)
commit 96fa6899ea (HEAD)

目前还不太清楚如何解释这些,所以情况是这样的:

在 中(…),git 列出了指向该提交的每个引用,例如(HEAD -> main, origin/main, origin/HEAD)表示HEAD、main、origin/main和origin/HEAD都指向该提交(直接或间接)
HEAD -> main意味着你当前的分支是main
如果该行显示的是HEAD,而不是HEAD ->,则表示您处于分离的 HEAD 状态(您没有当前分支)
如果我们用这些规则来解释上面的3个例子:结果是:

1)commit 96fa6899ea (HEAD -> main)方法:
   1-1).git/HEAD包含ref: refs/heads/main
   1-2).git/refs/heads/main包含96fa6899ea
 
2)commit 96fa6899ea (HEAD, main)方法:
   2-1).git/HEAD包含96fa6899ea(HEAD 处于“分离”状态)
   2-2).git/refs/heads/main还包含96fa6899ea
 
3)commit 96fa6899ea (HEAD)方法:
   3-1).git/HEAD包含96fa6899ea(HEAD 处于“分离”状态)
   3-2).git/refs/heads/main包含不同的提交 ID 或不存在

合并冲突:<<<<<<< HEAD很令人困惑

当您解决合并冲突时,您可能会看到类似以下内容:

<<<<<<< HEAD
def parse(input):return input.split("\n")
=======
def parse(text):return text.split("\n\n")
>>>>>>> somebranch

我发现HEAD这种情况非常令人困惑,我基本上只是忽略它。原因如下:

  1. 当你进行合并时,合并冲突与运行时的HEAD冲突相同。很简单。HEAD git merge

2)当你执行rebase时,HEAD合并冲突是完全不同的:这是你正在 rebase 的另一个提交HEAD。所以它与你运行 时的情况完全不同git rebase。之所以如此,是因为 rebase 的工作方式是先检出另一个提交,然后反复在其上挑选提交。

类似地,“我们的”和“他们的”的含义在合并和变基时被颠倒了。

事实上,HEAD根据我是否进行变基或合并而改变的含义对我来说确实太令人困惑了,我发现完全忽略HEAD并使用另一种方法来找出代码的哪部分是哪部分要简单得多。

关于术语一致性的一些想法

我认为,如果 git 围绕 HEAD 的术语在内部更加一致,那么 HEAD 会更加直观。

例如,git 会谈论“分离的 HEAD 状态”,但从不谈论“连接的 HEAD 状态”——git 的文档从来没有使用术语“连接”来指代HEAD。git 会谈论“在”分支上,但从不谈论“不在”分支上。

因此很难猜测 on branch main实际上是的反义词 HEAD detached。用户如何猜测这HEAD detached和分支有什么关系,或者和“在主分支上”有什么关系HEAD?

就这样!

如果我想到HEAD在 Git 中使用其他方法(尤其是 HEAD 出现在 Git 输出中的方式)会继续补充进来,如果你觉得 HEAD 令人困惑,我希望这篇文章有所帮助!

这篇关于git中的head到底是怎么工作的,十分钟就够了的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!



http://www.chinasem.cn/article/1124351

相关文章

怎么关闭Ubuntu无人值守升级? Ubuntu禁止自动更新的技巧

《怎么关闭Ubuntu无人值守升级?Ubuntu禁止自动更新的技巧》UbuntuLinux系统禁止自动更新的时候,提示“无人值守升级在关机期间,请不要关闭计算机进程”,该怎么解决这个问题?详细请看... 本教程教你如何处理无人值守的升级,即 Ubuntu linux 的自动系统更新。来源:https://

Ubuntu系统怎么安装Warp? 新一代AI 终端神器安装使用方法

《Ubuntu系统怎么安装Warp?新一代AI终端神器安装使用方法》Warp是一款使用Rust开发的现代化AI终端工具,该怎么再Ubuntu系统中安装使用呢?下面我们就来看看详细教程... Warp Terminal 是一款使用 Rust 开发的现代化「AI 终端」工具。最初它只支持 MACOS,但在 20

LinuxMint怎么安装? Linux Mint22下载安装图文教程

《LinuxMint怎么安装?LinuxMint22下载安装图文教程》LinuxMint22发布以后,有很多新功能,很多朋友想要下载并安装,该怎么操作呢?下面我们就来看看详细安装指南... linux Mint 是一款基于 Ubuntu 的流行发行版,凭借其现代、精致、易于使用的特性,深受小伙伴们所喜爱。对

macOS怎么轻松更换App图标? Mac电脑图标更换指南

《macOS怎么轻松更换App图标?Mac电脑图标更换指南》想要给你的Mac电脑按照自己的喜好来更换App图标?其实非常简单,只需要两步就能搞定,下面我来详细讲解一下... 虽然 MACOS 的个性化定制选项已经「缩水」,不如早期版本那么丰富,www.chinasem.cn但我们仍然可以按照自己的喜好来更换

SSID究竟是什么? WiFi网络名称及工作方式解析

《SSID究竟是什么?WiFi网络名称及工作方式解析》SID可以看作是无线网络的名称,类似于有线网络中的网络名称或者路由器的名称,在无线网络中,设备通过SSID来识别和连接到特定的无线网络... 当提到 Wi-Fi 网络时,就避不开「SSID」这个术语。简单来说,SSID 就是 Wi-Fi 网络的名称。比如

Ubuntu 怎么启用 Universe 和 Multiverse 软件源?

《Ubuntu怎么启用Universe和Multiverse软件源?》在Ubuntu中,软件源是用于获取和安装软件的服务器,通过设置和管理软件源,您可以确保系统能够从可靠的来源获取最新的软件... Ubuntu 是一款广受认可且声誉良好的开源操作系统,允许用户通过其庞大的软件包来定制和增强计算体验。这些软件

Ubuntu 24.04 LTS怎么关闭 Ubuntu Pro 更新提示弹窗?

《Ubuntu24.04LTS怎么关闭UbuntuPro更新提示弹窗?》Ubuntu每次开机都会弹窗提示安全更新,设置里最多只能取消自动下载,自动更新,但无法做到直接让自动更新的弹窗不出现,... 如果你正在使用 Ubuntu 24.04 LTS,可能会注意到——在使用「软件更新器」或运行 APT 命令时,

TP-LINK/水星和hasivo交换机怎么选? 三款网管交换机系统功能对比

《TP-LINK/水星和hasivo交换机怎么选?三款网管交换机系统功能对比》今天选了三款都是”8+1″的2.5G网管交换机,分别是TP-LINK水星和hasivo交换机,该怎么选呢?这些交换机功... TP-LINK、水星和hasivo这三台交换机都是”8+1″的2.5G网管交换机,我手里的China编程has

bat脚本启动git bash窗口,并执行命令方式

《bat脚本启动gitbash窗口,并执行命令方式》本文介绍了如何在Windows服务器上使用cmd启动jar包时出现乱码的问题,并提供了解决方法——使用GitBash窗口启动并设置编码,通过编写s... 目录一、简介二、使用说明2.1 start.BAT脚本2.2 参数说明2.3 效果总结一、简介某些情

AI绘图怎么变现?想做点副业的小白必看!

在科技飞速发展的今天,AI绘图作为一种新兴技术,不仅改变了艺术创作的方式,也为创作者提供了多种变现途径。本文将详细探讨几种常见的AI绘图变现方式,帮助创作者更好地利用这一技术实现经济收益。 更多实操教程和AI绘画工具,可以扫描下方,免费获取 定制服务:个性化的创意商机 个性化定制 AI绘图技术能够根据用户需求生成个性化的头像、壁纸、插画等作品。例如,姓氏头像在电商平台上非常受欢迎,