这两天发现一个学习git的小游戏,对于我这种git菜鸟也是有一定难度;
感觉挺有意思,游戏是闯关玩法。可以在学习中玩耍,又有一定的成就感
废话不多说,放链接: git小游戏
游戏中学到的命令总结一下:
下面说的节点就代表是提交记录
基础命令
基础
git commit
用于提交会新建一个节点
git branch
新建分支 但HEAD不会指向
git checkout -b xxx 新建分支的同时改变HEAD的指向
跟踪分支:
git checkout -b totallyNotMain o/main
就可以创建一个名为 totallyNotMain 的分支,它跟踪远程分支 o/main。
git branch -u o/main foo
这样 foo 就会跟踪 o/main 了。如果当前就在 foo 分支上, 还可以省略 foo:
git branch -u o/main
git merge
合并分支。主要是将别的分支拉过来进行合并
git merge。在 Git 中合并两个分支时会产生一个特殊的提交记录,它有两个父节点。翻译成自然语言相当于:“我要把这两个父节点本身及它们所有的祖先都包含进来。”
git rebase
也是用于合并分支。主要是将自己复制过另一个分支的提交记录。Rebase 实际上就是取出一系列的提交记录,“复制”它们,然后在另外一个地方逐个的放下去。会形成一个线性的节点
HEAD
HEAD 总是指向当前分支上最近一次提交记录。
大多数修改提交树的 Git 命令都是从改变 HEAD 的指向开始的。
修改HEAD指向也很简单,直接使用git checkout xxx xxx可以是分支名
也可以是某个提交记录上面的hash值(哈希值)
分离的 HEAD 就是让其指向了某个具体的提交记录而不是分支名。
相对引用修改HEAD
通过指定提交记录哈希值的方式在 Git 中移动不太方便。在实际应用时,并没有像本程序中这么漂亮的可视化提交树供你参考,所以你就不得不用 git log 来查查看提交记录的哈希值。
并且哈希值在真实的 Git 世界中也会更长(译者注:基于 SHA-1,共 40 位)。例如前一关的介绍中的提交记录的哈希值可能是 fed2da64c0efc5293610bdd892f82a58e8cbc5d8。舌头都快打结了吧…
因此此时我们可以使用相对引用进行快速修改指向
相对引用命令
使用 ^ 向上移动 1 个提交记录
当HEAD有两个父节点时,git checkout main^ 2 就是切换到另一个节点
例:git checkout main^ 就是当前main分支指向的提交记录的上一个
使用 ~ 向上移动多个提交记录,如 ~3
例:git checkout main~2 就是当前main分支指向的提交记录的上2个
撤销更改
git reset
git reset 通过把分支记录回退几个提交记录来实现撤销改动。你可以将这想象成“改写历史”。git reset 向上移动分支,原来指向的提交记录就跟从来没有提交过一样。注:git reset 对于远程分支无效
例:git reset HEAD~1 就将git 回到上一次提交记录
git revert
git revert HEAD
命令会在HEAD后新增一个提交记录,此时的提交记录是与上一个节点的提交记录一样的,也就是原来的那个记录不见了
git branch -f main HEAD
该命令可以移动分支到HEAD节点上
git cherry-pick <提交号>…
如果你想将一些提交复制到当前所在的位置(HEAD)下面的话, Cherry-pick 是最直接的方式了。我个人非常喜欢 cherry-pick,因为它特别简单。
提交号指的是哈希值,可以有多个
git rebase -i HEAD~3
想要移动节点,还可以使用交互式rebase
该命令会出现弹框,可对HEAD上的三个节点进行编辑(交换位置,删除)
git tag
标签可以(在某种程度上 —— 因为标签可以被删除后重新在另外一个位置创建同名的标签)永久地将某个特定的提交命名为里程碑,然后就可以像分支一样引用了。
更难得的是,它们并不会随着新的提交而移动。你也不能切换到某个标签上面进行修改提交,它就像是提交树上的一个锚点,标识了某个特定的位置。
例:git tag v1 C1
将这个标签命名为 v1,并且明确地让它指向提交记录 C1,如果你不指定提交记录,Git 会用 HEAD 所指向的位置。
可以直接 git checkout v1 进行切换
git describe
由于标签在代码库中起着“锚点”的作用,Git 还为此专门设计了一个命令用来描述离你最近的锚点(也就是标签),它就是 git describe!
git describe 的语法是:
git describe <ref>
可以是任何能被 Git 识别成提交记录的引用,如果你没有指定的话,Git 会以你目前所检出的位置(HEAD)。
它输出的结果是这样的:
<tag>_<numCommits>_g<hash>
tag 表示的是离 ref 最近的标签, numCommits 是表示这个 ref 与 tag 相差有多少个提交记录, hash 表示的是你所给定的 ref 所表示的提交记录哈希值的前几位。
当 ref 提交记录上有某个标签时,则只输出标签名称
远程
git clone
git clone 命令在真实的环境下的作用是在本地创建一个远程仓库的拷贝(比如从 github.com)。
git fetch
git fetch 做了些什么
git fetch 完成了仅有的但是很重要的两步:
1.从远程仓库下载本地仓库中缺失的提交记录
2.更新远程分支指针(如 o/main)
git fetch 实际上将本地仓库中的远程分支更新成了远程仓库相应分支最新的状态。
如果你还记得上一节课程中我们说过的,远程分支反映了远程仓库在你最后一次与它通信时的状态,git fetch 就是你与远程仓库通信的方式了!希望我说的够明白了,你已经了解 git fetch 与远程分支之间的关系了吧。
git fetch 通常通过互联网(使用 http:// 或 git:// 协议) 与远程仓库通信。
可以将 git fetch 的理解为单纯的下载操作。
git pull
git pull 就是 git fetch 和 git merge 的缩写!
先将提交拉取过来再进行合并
还有 git push --rebase
类似的 git pull --rebase 就是 fetch 和 rebase 的简写!
git push
git push 负责将你的变更上传到指定的远程仓库,并在远程仓库上合并你的新提交记录。一旦 git push 完成, 你的朋友们就可以从这个远程仓库下载你分享的成果了!
本地分支和远程分支的交互
参数:
git push origin main 将本地分支main提交远程main分支
git push origin main:bar 将本地分支main提交远程bar分支
git fetch origin main:bar 将远程分支main下载到本地bar分支
git pull origin main:bar 是上面的合并,下载了之后再自动进行合并
git push origin :bar 删除远程bar分支
git fetch origin :bar 新增本地bar分支