Git-Guide
Git入门学习
目录
- 引言( Read me first !)
- Git 基础概念
- Git安装与配置
- Git基本操作
- Git的‘版本控制’
- 分支与合并
- 远程仓库协作
- Git高级功能详解
- Git 指令的基本范式
- Git最佳实践
- 常见问题与解决方案
- 工具与扩展
- 结语
引言( Read me first !)
- 介绍版本控制系统的概念及其重要性
- Git的发展背景及其在行业中的地位
- 文章的目标和结构概述
- 本篇文章希望通过带你一步一步复现git中的操作,来更好地了解Git的功能与运用
- 本文基于ubuntu22.04编写, 文件、目录的操作都是用bash命令完成,有些命令可能与windows的cmd命令有不同,也可以直接不用命令行操作,使用git的时候右击鼠标,选择“open git bash here ”
声明: 为了让没接触过Git的小伙伴能快速入门,在本文的前半部分以实际操作为主,可能有部分词汇不太严谨,更专业的说法以及原理将在后面呈现
Git 基础概念
如果光看概念没有太明白也不用担心,跟着接下来的实践能更好地理解Git
背景:集中式 vs 分布式
-
集中式版本控制系统(CVCS)
- 代表工具:SVN、CVS
- 所有版本记录都保存在中央服务器上,开发者需要联网才能提交或更新代码。
- 优点:管理集中,权限控制简单。
- 缺点:依赖服务器,一旦服务器故障可能导致版本丢失;多人协作容易产生冲突。
-
分布式版本控制系统(DVCS)
- 代表工具:Git、Mercurial
- 每个开发者的本地仓库都保存完整版本历史,操作大多在本地完成。
- 优点:不依赖中央服务器、操作灵活、支持离线开发,容易进行分支和合并。
- 缺点:初学者学习曲线稍陡,仓库可能体积大。
Git 核心概念
+-------------------+
| 远程仓库 (Remote) |
| origin/main |
+---------+---------+
^
| git pull / fetch
|
+---------+---------+
| 本地仓库 (Local) |
| 提交记录 Commit |
| 分支 Branch |
| 标签 Tag |
+---------+---------+
^
| git commit
|
+---------+---------+
| 暂存区 (Staging) |
| git add 文件到此处 |
+---------+---------+
^
| 修改文件
|
+---------+---------+
| 工作区 (Working) |
| 正在编辑的文件 |
+-------------------+
Git 工作流程
Git 的工作目录大致分为四层:
-
工作目录(Working Directory)
- 就是你平常看到的项目文件夹
- 可以修改、编辑、删除文件
-
暂存区(Staging Area / Index)
- 临时存放即将提交的文件
- 通过
git add将文件从工作区放入暂存区
-
本地仓库(Local Repository)
- 通过
git commit将暂存区的内容保存到本地仓库 - 每次提交都会生成一个唯一 ID
- 通过
-
远程仓库(Remote Repository)
- 位于远程服务器(如 GitHub、GitLab)
- 通过
git push上传本地提交,通过git pull获取远程更新
本地的工作流程:主要在工作区、暂存区、本地仓库中进行
最主要的内容为:
- 将工作区的文件添加到暂存区;
- 将暂存区的文件添加到仓库;
- 从仓库中恢复不同版本的文件

但是划分成这三个区域究竟有什么用呢?
在图形化界面中,我们往往只能从资源管理器中看到工作区。也就是普通的目录

而我们的缓存区和仓库通常是储存在一个名为.git的隐藏文件夹里的
使用ls -a可以显示所有的目录

打开.git目录

那么文件夹里有这么多东西,又分别是用来干嘛的呢?
下面简单介绍一下 .git 文件夹里这些主要文件和目录的作用:
1. branches/
- 作用:保存“本地分支和远程分支的映射关系”。
- 但是这个目录在现代 Git 里基本上已经废弃了,几乎总是空的。
Git 现在用refs/heads/和refs/remotes/来管理分支。
2. config
-
作用:当前仓库的配置文件。
-
内容:存储仓库级别的 Git 配置,比如远程仓库地址、用户名邮箱、分支默认推送策略等。
-
例子:
1
2
3
4
5
6
7
8
9[core]
repositoryformatversion = 0
filemode = true
[remote "origin"]
url = https://github.com/user/repo.git
fetch = +refs/heads/*:refs/remotes/origin/*
[branch "main"]
remote = origin
merge = refs/heads/main
3. HEAD 这一部分一定要耐心看到最后!很关键!
分支相关说明:
在 Git 中,分支实际上就是一个指向特定提交的可变指针。当你创建一个新分支时,Git 会创建一个新的指针来跟踪该分支的提交历史。
简单来说,提交是一个实在的物体,这个物体有它的id;而分支则是一个指针,指向某一次的提交,并会随着新的提交而移动
-
HEAD作用:一般来说指向 当前 检出的 分支(或具体的提交)。HEAD 是 Git 中一个特殊的指针,用于记录当前工作目录所处的状态。在大多数情况下,HEAD 相当于一个"你在这里"的标记,指向你正在工作的分支的最新提交。在一次新的提交中,创建的对象会以HEAD作为自己的父提交
上图更容易理解:

-
HEAD内容:-
如果你在某个分支上,也就是指向了这个分支,会是:
1
ref: refs/heads/main
-
如果你处于 游离 HEAD 状态(detached HEAD),比如
checkout到了某一次提交,它会直接保存提交哈希:1
3f2a4e9b9d8f7a6c...
这种状态下,后续的commit会游离在分支之外
-
这就像C++中的一个变量,以及指向这个变量的指针,以及指向指针的指针 ;
让我们用这张图来更清晰地认识一下游离的情况:
用checkout指令使HEAD指向提交C2

4. index
- 作用:Git 的暂存区(staging area)。
- 类型:是一个二进制文件(不是纯文本)。
- 内容:记录哪些文件已经被
git add,以及对应的 文件快照哈希、路径、修改时间等。 - Git 提交时就是根据
index里的内容来生成新的 commit。
5. logs/
-
作用:保存 Git 的操作日志(特别是分支引用的移动历史)。
-
主要有:
logs/HEAD:记录 HEAD 每次切换或提交的移动。logs/refs/heads/*:记录每个分支的提交历史(包括 rebase、reset)。
-
⚠️ 和
git log不一样,git log只看提交历史;而 reflog(这些日志)能看到被删除或移动的提交(救命工具)。
6. packed-refs
-
作用:保存“被打包的引用”(refs)。
-
说明:Git 原本在
refs/heads/、refs/tags/下保存分支/标签,但如果分支和标签很多,Git 会把它们“打包”进packed-refs文件里,提升性能。 -
例子:
1
23f2a4e9b9d8f7a6cf5f39b2e2e2c1a commit refs/tags/v1.0
8e9f7a6c3f2a4e9b9d8f7a6cf5f39b2e commit refs/tags/v1.1
7. description
-
作用:仓库描述文件,主要给 GitWeb 这种 Web 界面用。
-
默认内容:
1
unnamed repository; edit this file 'description' to name the repository.
-
⚠️ GitHub、GitLab 之类不用这个文件,它们用自己的数据库。
8. hooks/
-
作用:保存 Git 钩子脚本。
-
钩子 = Git 操作时触发的脚本,可以自定义自动化流程。
-
常见钩子:
pre-commit:提交前执行(比如自动代码格式化)。commit-msg:检查提交信息。pre-push:推送前检查。
-
默认是
.sample结尾的示例脚本。
9. info/
-
作用:存放仓库的补充信息。
-
常见文件:
-
info/exclude:类似.gitignore,但是只作用于当前仓库,不随仓库共享。
例如:1
2*.log
temp/
-
10. objects/
-
作用:存放 Git 的所有 对象(Object),这是 Git 的核心。
-
Git 的一切数据(commit、tree、blob、tag)都是对象,按哈希值分目录存储。
-
结构:
1
2
3
4
5
6
7objects/
|-- ab/
| |-- cd1234... # 对象文件
|-- info/
|-- pack/
|-- pack-xxxx.idx
|-- pack-xxxx.pack -
说明:
- 松散对象:直接存储在
objects/xx/xxxxxx。 - 打包对象(packfile):存储在
pack/里,多个对象压缩合并,提高性能。
- 松散对象:直接存储在
11. refs/
-
作用:存放所有引用(分支、标签、远程分支)。
-
结构:
1
2
3
4refs/
|-- heads/ # 本地分支
|-- remotes/ # 远程分支
|-- tags/ # 标签 -
每个文件里就是一个 commit 的 id (哈希值)。
-
例如
refs/heads/main内容可能是:1
3f2a4e9b9d8f7a6c...
如果不是很明白别着急,可以跟着下面Git的基本操作完之后再回顾
而关于远程仓库,请看远程仓库协作部分
Git安装与配置
安装git
- 在不同操作系统(Windows、macOS、Linux)上安装Git
-
Windows: git-for-windows下载
根据自己电脑的配置下载对应的版本:绝大多数笔记本都是x64架构 ;
安装时跟随指引正常勾选选项即可 -
Linux : 这里我以我的Ubuntu22为例 ,其他Linux发行版也同样是在bash里操作, CTRL + ALT + T 打开终端,输入:
-
1 | sudo apt install git |
可以查看git的版本来判断git是否安装成功
1 | git --version |
如果输出版本信息,则说明安装成功
配置git
- 基本的Git配置:用户信息
当你第一次使用git的时候,我们需要设置以下你的用户信息邮箱、用户名
我们可以使用以下命令为我们的Git配置一下
1 | git config --global user.name "你的用户名" |
这里的命令config , 中文翻译过来就是配置的意思
命令参数 --global ,中文是全局变量,用来表示配置全部的git环境
- 配置SSH密钥以连接远程仓库
首先需要注册一个github账号来进行以下的操作。具体原理请看 远程仓库协作
Git基本操作
我们首先从最简单的操作出发,再来解释背后发生的原理
初始化仓库:
我们可以使用git init 来初始化本地仓库,或者使用 git clone来将远程仓库克隆下来(见远程仓库协作)
这里我们以本地化为例, CTRL + ALT + T 打开终端 (如果是Windows,可以直接新建文件夹),输入:
- 创建一个名为testGit的文件夹
1 | mkdir testGit |
- 进入创建的目录
1 | cd testGit |
- 使用
git init初始化
1 | git init |

文件状态管理:
最常见命令git status、git add、git commit、(git rm)
1.git status:
“status”即状态的意思,该条命令用于查看当前的状态
我们首先在当前的目录创建一个文件,随后再执行status命令
1 | touch test1.cpp |
可以看到输出了如下图的状态

每一栏分别是:
- On branch 现在在哪一条分支上
- Commit state 提交的状态
- Changes to be commited 缓存区未被提交的文件
- untracked 工作区未被追踪的文件
2.git add 指定了你要在工作区追踪的文件 , add以后的文件会被储存在缓存区
我们不妨再创建一个文件,并查看状态
1 | touch test2.cpp |

这是我们可以看到,两个文件都没有被跟踪
我们使用add命令将test1加入缓存区,并再次查看状态
1 | git add test1.cpp |

现在,test1.cpp已经成功地被追踪了,而test2.cpp还是未追踪状态
除了指定单个文件,add也可以指定所有的文件
1 | git add --all |
这样所有的文件都被追踪了

至于更多的指令选项,我们可以使用–help来查看,
请见Git/bash 帮助
3.git commit
“commit”即提交的意思 ,可以将缓存区的文件提交到本地的仓库
我们使用commit命令将test提交 ,
-m是“message”的缩写,后面使用" "来键入这次提交的描述信息
1 | git commit -m "commit test" |
可以看到,test已经成功提交了

4.git rm
如果我们直接从工作区中删除test2,可以看到本地仓库中test2仍然存在,

需要额外使用git add来追踪文件删除这一状态,再将删除commit到仓库

为此,可以直接使用git rm指令,将test2同时从工作区和仓库中删除
执行完之后可以看到ls没有输出,代表目录是空的

Git的‘版本控制’
而Git真正强大的地方在于 他会用一个生成的id来记录你所提交的每一个版本,
而我们可以使用这些id来回溯我们的代码,即进行版本控制
接下来我们学习如何查看提交历史,回滚历史记录
查看提交历史:git log 和 git show
使用git log来查看当前的历史提交记录

从图中可以看到我们的提交记录,每一行表示:
- 某一次提交的id
- 提交的作者
- 提交的时间
我们也可以使用git log "filename"来查看某个特定文件的历史提交
1 | touch test1.cpp |
使用git show来查看最近一次提交的记录,或者指定查看的版本号和文件
1 | git show |
— ·
撤销更改&回滚历史记录
git checkout、git reset、git revert
在开发过程中,我们经常会遇到以下几类需求:
- 丢弃未保存的修改(代码写错了,不想要了)。
- 撤销已经 add 到暂存区的内容。
- 回到某个历史版本(彻底重置)。
- 撤销某次错误提交,但保留历史记录(更安全)。
Git 提供了三种常用指令来处理:
-
git checkout—— 丢弃工作区的修改1. 如果你改了某个文件,但还没执行 git add, 可以用下面的命令恢复成最近一次提交的状态, 这样文件会回到最后一次提交时的内容,未保存的修改会丢失。
1 | git checkout -- <file> |
2. 而如果你已经执行了`git add `, 之后又修改了工作区的文件 ,
工作区的文件会回到暂存区的状态
也就是说checkout – file 的本质是:用暂存区覆盖工作区。
如果暂存区里没有这个文件的改动,就用 HEAD(最近一次提交)的版本覆盖。
git reset—— 回退到指定提交(可能丢历史)
1 | git reset <选项> '回滚的id' |
git reset 会改变当前分支的指向,让分支回到某个历史提交。
它有三种常见模式:
--soft
仅回退分支指针到指定提交 , 保留暂存区和工作区的修改
相当于 工作区、暂存区不变 , 仓库删除指定提交后面的版本
常用于:撤销提交,但想重新修改提交信息或合并到下一个提交
--mixed(默认模式)
回退分支指针,并清空暂存区
工作区文件保留,但变为“未暂存状态”
相当于 工作区不变,暂存区清空,仓库删除指定提交后面的版本
常用于:取消 git add
1 | git reset --mixed <commit-hash> |
--hard
回退分支指针,同时清空暂存区和工作区
所有未保存的修改都会丢失
常用于:彻底回退到某个版本
1 | git reset --hard <commit-hash> |
git revert—— 撤销提交,但保留历史(推荐)
git revert 会生成一个新的提交,用来“抵消”指定的提交。这样历史记录不会丢失。
举例
1 | # 当前分支提交历史 |
适合在团队协作中撤销错误提交
分支与合并
在 Git 中,分支(branch) 是指向某个提交的可移动指针。
它的作用是让我们在主线开发之外,开辟出一条独立的开发路线,用于开发新功能、修复 bug,而不会影响主分支的稳定性。
1. 分支的概念及其重要性
- 默认分支:新建仓库时会自动生成一个主分支(通常叫
main或master)。 - 作用:通过分支,我们可以同时进行多条开发任务,比如一个分支写新功能,一个分支修 bug,互不干扰。
- 优势:降低协作冲突风险,代码管理更清晰。
2. 创建和切换分支
- 查看所有分支
1 | git branch |
- 创建分支
1 | git branch <branch-name> |
- 切换分支
1 | git checkout <branch-name> |
- 创建并切换分支
1 | git checkout -b <branch-name> |
3. 合并分支
当一个分支上的工作完成后,需要把它的修改合并到主分支:
1 | git checkout main |
- 如果两个分支没有冲突,会直接合并生成一个新的提交。
- 如果修改了同一文件的同一位置,就会发生 冲突,需要手动编辑文件解决冲突,然后:
1 | git add <file> |
那么我们如何手动解决冲突呢?
那么我们如何手动解决冲突呢?具体步骤如下:
-
当合并出现冲突时,Git会在冲突文件中用特殊标记标出冲突区域:
1
2
3
4
5<<<<<<< HEAD
当前分支的内容
=======
要合并分支的内容
>>>>>>> branch-name -
手动编辑文件,选择保留其中一个版本的内容,或者进行适当修改合并两种修改。需要完全删除
<<<<<<<、=======和>>>>>>>这些标记行。 -
冲突解决后,使用
git status命令可以查看哪些文件仍处于未合并状态。 -
对于每个解决完冲突的文件,都需要执行
git add将其标记为已解决。 -
最后执行
git commit完成合并。此时Git会自动生成合并提交信息,也可以使用-m参数自定义提交信息。
示例场景:假设你正在开发新功能,同事同时修改了同一个文件的同一部分。当你合并他的分支时就会遇到冲突,需要手动决定保留哪种修改,或者结合两种修改。(这一部分在接下来的远程仓库的PR中也也会提及~)
4. 变基操作(git rebase)
在 Git 里,每个提交都有一个 父提交(parent commit),表示它基于哪个版本修改的
这里不同分支之间的 父提交 在下图中用 \ 表示
git rebase 的作用是修改提交之间的父子关系, 把一个分支上的提交“搬运”到另一个分支的后面,让提交历史更加整洁。
例如:
1 | main: A -- B |
执行:
1 | git checkout feature |
结果:
1 | main: A -- B |
C、D被重新“复制”成C'、D',接在B之后。- 提交历史看起来像一条直线,更加清晰。
⚠️ 注意:rebase 会重写历史,不要在已经 推送到远程并被他人使用的分支 上使用。
5. 查看分支之间的区别
在 Git 中,我们经常需要比较不同分支之间的差异。以下是几种常用的分支比较方法:
5.1 比较两个分支的所有差异
使用 git diff 命令可以比较两个分支之间的所有差异:
1 | git diff branch1..branch2 |
这个命令会显示两个分支之间所有不同的文件及其具体修改内容。例如:
- 新增的文件会显示为绿色
- 删除的文件会显示为红色
- 修改的文件会显示具体的行变化
5.2 比较特定文件的差异
如果只想比较某个特定文件在两个分支中的差异:
1 | git diff branch1..branch2 -- path/to/file |
这在大型项目中特别有用,可以快速定位特定文件的变化。
5.3 查看提交历史差异
要查看两个分支之间的提交历史差异:
1 | git log branch1..branch2 |
这会显示存在于 branch2 但不在 branch1 中的所有提交。如果想看双向差异,可以加上 --left-right 选项。
5.4 图形化比较工具
对于更直观的比较,可以使用图形化工具:
git difftool:调用配置的 diff 工具(如 Beyond Compare, KDiff3 等)- IDE 内置的版本控制工具(如 VS Code, IntelliJ IDEA 等)
5.5 查看分支合并情况
使用以下命令可以查看哪些分支已经合并或未合并到当前分支:
1 | git branch --merged # 显示已合并的分支 |
应用场景示例
- 代码审查:在合并分支前,先查看所有修改
- 冲突解决:定位两个分支的具体差异点
- 版本比较:比较不同版本间的功能差异
- 代码同步:确认哪些修改需要同步到其他分支
记住,在比较分支差异时,最好先确保本地分支是最新的(使用 git fetch 获取远程更新)。
远程仓库协作
常用操作:
- 添加远程仓库:
git remote add - 推送和拉取更改:
git push和git pull - 克隆远程仓库:
git clone - 协作流程:Fork、Pull Request(PR)
添加远程仓库
对于Git的远程仓库,现在使用最广泛的就是GitHub
我们现在将刚刚创建好的本地仓库上传
-
我们首先创建一个GitHub账号
-
配置本地的ssh
1
ssh-keygen -t rsa -C "你的git账号"
ssh是我们要建立的通讯协议的类型,keygen是"key generate"即“生成密钥”的缩写
-t是type即类型 , 这里指定的密钥类型是rsa
-C是comment ,为生成的这个密钥进行了注释,方便区分

1 | #linux |
这里可以看到.ssh文件夹里的文件,这两个是我们生成的私钥和公钥

打开公钥文件
1 | #Linux |

-
连接到GitHub



-
检验ssh连接是否成功
1 | ssh -T git@github.com |
第一次会提示确认 GitHub 的主机指纹), 输入yes
1 | The authenticity of host 'github.com (IP地址)' can't be established. |
1 | Hi 用户名! You've successfully authenticated, but GitHub does not provide shell access. |
- 创建远程仓库



- 在目录里添加远程仓库(替换为你自己的仓库的ssh地址!)
1 | cd testGit #打开目录 |
- 推送到远程仓库
使用git push命令
(建议先用status查看一下你的主分支是叫main还是master)
1 | touch test.cpp |
回到github的页面,刷新之后就能看到文件上传成功了

- 在远程仓库中添加README.md , 用pull拉取更改
github会建议你创建一个README.md文件来介绍你的仓库,我们点击上一张图片中的Add a README, 随便输入一点之后 点击右上角的绿色commit change
创建完之后,可以使用pull来将远程仓库中新增的变化拉下来
1 | git pull origin master |
可以看到README.md已经成功被拉取到了本地
克隆远程仓库
我们还可以直接把远程的仓库clone下来:
- 创建新的目录并进入
1 | mkdir newTest |
- 克隆已经存在的仓库
1 | git clone git@github.com:S1mpleWind/testGit.git #替换成你自己的 |
- 检验是否克隆成功
1 | ls |
创建PR(Pull Request)
当你在GitHub上与团队协作开发项目时,Pull Request(PR) 是一个核心的协作机制。它不仅是代码变更的提交方式,更是团队代码评审和讨论的重要平台。
PR的主要作用
- 代码合并请求:请求将你的分支(如feature/login)合并到目标分支(通常是main或master)
- 代码审查:团队成员可以查看你的变更,提出修改建议
- 持续集成:自动触发CI/CD流程,运行测试和构建
- 讨论平台:针对特定变更进行技术讨论
创建PR的标准流程
-
准备工作:
- 确保本地分支是最新的(git pull)
- 解决所有代码冲突
- 通过本地测试
-
推送分支:
1
git push origin your-branch-name
-
创建PR:
- 在GitHub仓库页面点击"New pull request"按钮
- 选择正确的源分支(你的分支)和目标分支
- 填写清晰的标题和描述(建议使用模板)
-
完善PR信息:
- 关联相关issue(使用"Closes #123"语法)
- 添加适当的标签(如bug, enhancement)
- 指定审阅者(reviewers)
-
持续更新:
- 根据review意见修改后,直接push到原分支
- PR会自动更新,无需新建
最佳实践
- 保持PR规模适中(建议300行以内)
- 一个PR只解决一个明确的问题
- 提供清晰的修改背景和测试说明
- 使用GitHub的预览功能检查变更
实际应用场景
示例:你开发了一个用户登录功能
- 在本地创建feature/login分支开发
- 完成开发后推送到远程仓库
- 创建PR请求合并到main分支
- 团队leader审查代码后提出优化建议
- 你修改后重新push,通过审查后合并
通过PR流程,团队可以确保代码质量,促进知识共享,并保持主分支的稳定性。### 创建PR(Pull Request)
当你在github上和你的团队进行协作的时候,PR往往是必不可少的一部分。它允许开发者将代码变更通知团队成员,请求将分支合并到主分支。
Git高级功能详解
1. 使用标签标记重要版本:git tag
Git标签是用于标记特定提交(如版本发布)的永久引用。与分支不同,标签创建后不会改变。标签分为两种类型:
- 轻量标签(lightweight):只是一个指向特定提交的指针
- 附注标签(annotated):存储为Git数据库中的完整对象,包含打标签者的名字、邮箱、日期和标签信息
常见用法示例:
1 | # 创建轻量标签 |
使用tag能很好的帮你标记在开发过程中迭代版本的代码
2. 暂存更改:git stash
git stash命令用于临时保存工作目录和暂存区的修改,而不需要提交。这在需要快速切换分支但当前工作未完成时特别有用。
详细用法:
1 | # 保存当前工作状态(包括未跟踪的文件) |
3. 交互式暂存:git add -p
交互式暂存允许你选择性地暂存文件的特定部分,而不是整个文件。这对于将大改动分解为逻辑上独立的提交非常有用。
操作步骤:
- 运行
git add -p或git add --patch - Git会显示每个改动"块"(hunk)并询问操作:
- y: 暂存该块
- n: 不暂存该块
- q: 退出
- s: 分割当前块为更小的块
- e: 手动编辑当前块
- 重复此过程直到完成所有选择
示例场景:
当你在一个文件中同时修复了两个bug,可以使用交互式暂存将它们分别提交:
1 | git add -p bugfix.py |
4. 子模块管理:git submodule
子模块允许你将一个Git仓库作为另一个Git仓库的子目录,保持它们的独立性但又能协同工作。
常用命令:
1 | # 添加子模块 |
管理技巧:
- 子模块有自己的.git目录,存储自己的提交历史
- 主项目只记录子模块的特定提交,不跟踪其内容变化
- 修改子模块后需要在主项目中提交子模块引用变更
- 使用
--recursive选项时,递归操作会应用到所有嵌套子模块
应用场景:
- 将共享库作为子模块包含在多个项目中
- 分离核心代码和依赖组件
- 管理大型项目中的独立功能模块# Git高级功能
- 使用标签标记重要版本:
git tag - 暂存更改:
git stash - 交互式暂存:
git add -p - 子模块管理:
git submodule
Git 指令的基本范式
Git 的命令和普通的bash命令一样,通常遵循以下结构:
git <指令> [选项] [参数]
- 指令(Command):表示要执行的具体操作,例如 clone、commit、push。
- 选项(Option):用于调整指令的执行方式,通常以 - 或 – 开头,例如 -m、–all。
- 参数(Argument):指令或选项所作用的对象,例如文件路径、分支名、提交 ID 等。
例如:
1 | git commit -m "初始化项目" |
其中:
commit 是指令;
-m 是选项;
“初始化项目” 是参数。
这样可以更清晰地理解 Git 命令的组成与用法。
如果想要每一条指令具体的选项和参数,可以使用--help选项来查看
1 | git commit --help |
Git最佳实践
- 提交信息的规范(如Conventional Commits)
- 分支管理策略(如Git Flow、GitHub Flow)
- 避免常见错误(如强制推送、大文件提交)
常见问题与解决方案
如何撤销错误的提交
-
撤销本地未推送的提交
- 使用
git reset --soft HEAD~1保留更改但撤销提交 - 使用
git reset --hard HEAD~1彻底丢弃更改 - 示例:
git reset --soft HEAD~1 && git commit -m "正确的提交信息"
- 使用
-
撤销已推送的提交
- 使用
git revert <commit-hash>创建反向提交 - 适用于共享仓库的撤销
- 示例:
git revert abc1234然后推送反向提交
- 使用
-
修改最近一次提交
git commit --amend修改提交信息或内容- 适用于仅修改最后一次提交的情况
如何恢复误删的分支
-
查找删除的分支记录
git reflog查看所有操作历史- 查找删除前的commit记录
-
恢复分支方法
- 通过commit hash恢复:
git branch <branch-name> <commit-hash> - 示例:
git branch feature/login abc1234
- 通过commit hash恢复:
-
预防措施
- 推送分支到远程:
git push origin <branch-name> - 定期备份重要分支
- 推送分支到远程:
如何处理大文件或敏感信息
-
大文件处理方案
- 使用Git LFS (Large File Storage)
- 安装后配置:
git lfs install - 跟踪大文件:
git lfs track "*.psd"
-
移除已提交的敏感信息
- 使用
git filter-branch或BFG Repo-Cleaner - 示例:
bfg --replace-text passwords.txt my-repo.git - 完成后强制推送:
git push --force
- 使用
-
预防措施
- 添加.gitignore文件排除特定文件
- 使用环境变量存储敏感信息
- 定期检查仓库中的大文件:
git count-objects -vH# 常见问题与解决方案
工具与扩展
图形化工具
- GitHub Desktop:微软开发的跨平台Git图形界面,特别适合GitHub用户,提供直观的提交历史查看、分支管理和冲突解决界面
- SourceTree:Atlassian推出的免费Git客户端,支持Windows和Mac,提供强大的可视化分支管理功能
- GitKraken:流行的跨平台Git客户端,具有漂亮的UI设计和丰富的功能集,包括内置合并工具和GitFlow支持
IDE中的Git集成
- VS Code:内置Git支持,提供源代码管理面板、差异查看器和提交界面,可通过扩展(如GitLens)增强功能
- IntelliJ IDEA:提供完整的Git集成,包括可视化提交、分支管理和冲突解决工具,支持GitFlow工作流
- Eclipse:通过EGit插件提供Git支持,包括提交历史查看、分支管理和远程仓库操作
第三方服务
- GitHub:最流行的Git托管平台,提供代码托管、协作工具和CI/CD集成,支持GitHub Actions自动化
- GitLab:开源Git平台,提供完整的DevOps工具链,包括CI/CD、容器注册表和项目管理功能
- Bitbucket:Atlassian的Git解决方案,与Jira深度集成,适合企业开发团队
- Azure DevOps:微软的企业级Git托管服务,提供完整的ALM工具链和CI/CD流水线
其他实用工具
- Tower:macOS平台的付费Git客户端,提供直观的界面和强大的功能
- Fork:轻量级的Git客户端,专注于性能和用户体验
- Git-Cola:开源的跨平台Git图形界面,适合Linux用户
结语
Git的核心价值总结
Git作为分布式版本控制系统,其核心价值主要体现在以下几个方面:
-
版本控制能力:Git可以精确记录文件的历史变更,包括谁在什么时候修改了什么内容,形成了完整的开发历史记录。
-
分布式架构:每个开发者都拥有完整的仓库副本,可以在离线状态下工作,大大提高了开发灵活性和可靠性。
-
分支管理优势:Git的轻量级分支模型使得创建、合并和管理分支变得极其简单,支持高效的并行开发流程。
-
数据完整性保障:采用SHA-1哈希算法确保所有提交和文件内容都是不可篡改的,为代码提供了可靠的安全保障。
-
高效性能:大多数操作都在本地完成,响应速度快,能够轻松处理大型项目和复杂的历史记录。
学习资源推荐
官方文档
- Pro Git书籍(免费在线版):由Git官方维护,内容全面且权威,是学习Git的最佳起点。
- Git官方文档:包含所有Git命令的详细说明和使用示例。
在线课程
- GitHub Learning Lab:交互式学习平台,通过实践项目学习Git和GitHub。
- Udemy的Git Complete课程:从入门到进阶的系统性课程,包含大量实操练习。
推荐书籍
- 《Pro Git》(Scott Chacon著):Git核心开发团队成员编写,内容全面且深入。
- 《Git权威指南》(蒋鑫著):中文Git经典教程,适合中国开发者阅读。
- 《Version Control with Git》(Jon Loeliger著):侧重实际工作场景中的Git使用技巧。
鼓励实践与进一步探索
Git的学习需要通过大量实践才能真正掌握。建议:
-
创建个人项目仓库:用Git管理自己的个人项目,如博客、小程序等,从简单的版本控制开始练习。
-
参与开源项目:通过GitHub等平台参与开源项目,体验团队协作开发流程,学习如何处理合并请求和解决冲突。
-
尝试高级功能:当熟悉基础操作后,可以探索Git的高级功能,如:
- 交互式rebase
- 子模块管理
- 钩子脚本
- 二分查找定位问题提交
-
持续学习新技术:Git生态系统不断发展,可以关注Git LFS(大文件存储)、Git Flow等工作流程,以及Git与其他DevOps工具的集成。
记住,Git是一个工具,最重要的是理解其背后的设计理念和工作原理,这样才能灵活应对各种复杂场景。祝你在Git的学习和使用中不断进步!
欢迎大佬们的批评指正