简介
之前关于head的文章中,保留了一个问题:
分支引用总是指向最新的一个commit吗?
先给结论
分支(比如 master、dev)总是指向“该分支的最新一次提交” 。
但注意:
它不是指向“整个仓库最新的 commit”,
而是指向“自己这条线的最新 commit”。
1.分支到底是什么?
在 Git 里:
分支本质就是一个可以移动的指针。
比如:
A --- B --- C (master)
这里:
- C 是最新 commit
- master 只是一个指向 C 的指针
提交时会发生什么?
当你在 master 上:
git commit
Git 会:
创建新 commit D
把 master 指针从 C 移动到 D
变成:
A --- B --- C --- D (master)
所以:
master 总是指向它自己的最新 commit
多个分支时的情况:
假设:
A --- B --- C (master)
\
D --- E (dev)
现在:
- master 指向 C
- dev 指向 E
注意:
E 是整个仓库最新 commit,
但 master 不会自动移动到 E。
所以,本地仓库 = .git 里的 commit 对象 + 指针(分支)
总结:
用一句话彻底理解
Git 不是“分支包含提交”。(重点)
而是:
commit形成一棵树,
分支只是指向树上某个节点的标签。
所以:
前面两篇文章所提到的head,与commit,和分支的关系如下:
| 概念 | 本质 |
|---|---|
| commit | 不可变对象 |
| branch | 指向 commit 的指针 |
| HEAD | 指向当前 branch |
所以,为什么说 Git 创建分支几乎是零成本
因为分支只是一个指向一个commit的指针
2.查看当前分支
查看当前在哪个分支
git branch
或者
git branch -vv
带 * 的就是当前分支。
3.创建分支
创建新分支(但不切换):
git branch dev
意思是:
在当前 commit 位置创建一个叫 dev 的指针
不会自动切换。
创建并切换(常用):
git checkout -b dev
-b 是 branch 的缩写,意思是 "创建并切换到新分支" 。
这条命令的完整含义是:
- 创建一个名为
dev的新分支 - 立即切换到这个新分支
相当于连续执行了以下两条命令:
bash
git branch dev # 创建 dev 分支
git checkout dev # 切换到 dev 分支
4.切换分支
切换就简单了
git checkout dev
就行
5.合并分支
merge 永远是:
把“指定分支”合并到“当前分支”
比如,你想把dev合并到master
你需要先切换回 master
git merge dev
意思是:
把 dev 分支的内容合并到当前分支
如果是快进合并(fast-forward):
A --- B --- C --- D --- E (master, dev)
如果期间 master 也有提交,会生成 merge commit:
A --- B --- C --- F (master)
\ /
D --- E (dev)
6.推送新分支
如果需要将本地新建的分支推送到远程
git push -u origin dev
-u 是 --set-upstream 的简写,意思是 "设置上游分支" 。
这条命令的完整含义是:
- 推送:将本地的
dev分支推送到远程origin的dev分支 - 建立跟踪关系:将本地的
dev分支与远程的origin/dev分支关联起来
7.分支的作用
为什么要创建分支?
一句话:
分支是为了“隔离变化”。
分支的作用是:
- 不影响主线(例如master是主线,主线需要稳定,而不是不停的上新的功能)
- 可以独立开发
- 可以随时丢弃
- 可以安全合并
什么情况下要创建分支?
- 开发新功能(最常见)
- 修复 Bug
- 做实验
- 多人协作,每个人一个分支
开发流程:
- 创建自己的分支
- 提 MR
- 代码 review
- 合并到目标分支
- 删除自己的分支
这是现在最主流的模式。
一个仓库在团队协作中,是必然少不了分支的操作,到这里,我们已经通过head、commit、branch这三篇文章基本认识了git
其中rebase、merge是啥呢?
后续继续探讨更多和团队合作相关的操作