Git常用命令简介

Git 简介

关于Git,对于程序员肯定不陌生,全球最大开源平台 GitHub 便是基于 Git 创建,Git 与 GitHub 的关系,从名字上就可以看出 GitHub 就是基于 Git 的一个仓库( hub ), Git 是一个分布式版本控制软件,而 GitHub 就是基于该版本控制软件而创建的一个网站。为了更好学习,可以到learngitbranching 练习相应的操作。

有些人会觉得 Git 与 GitHub 其实差不多,但实际上,如果你需要往 GitHub 这个网站上传你的代码,那么你需要通过 Git 分布式版本控制软件来上传你的代码,但是你要查找别人的代码,那么你就需要从 GitHub 这个网站上搜索,对于网站的操作,并不会很麻烦,有图形化界面,所以我们的目标应该是先放在对Git这个分布式版本控制软件的使用。

Git是分布式版本控制软件,那么什么叫分布式,什么又叫版本控制软件。对于分布式,你可以理解为“鸡蛋不能放在同一个筐里”,版本控制可以理解为,你导师要你写一份论文,但是每次你提交论文给你的导师,他都会提一些修改,你为了避免改后的论文比之前的还要糟糕,你把每次提交的论文都保存下来,然后你的论文就变成下面这样的形式:

"paper1.docx"
"paper2.docx"
"paper3.docx"
...

那么,如果你使用了版本控制软件之后,你就可以在每次修改之后把每次修改的内容写一个概要,但是你的论文文件就只有一个文件,就不会像前面那样会产生无数个文件,到最后连自己都不知道哪个是最新的了,这就是版本控制。那么你的文件就相当于那些 "鸡蛋",分布式就是你把这些“鸡蛋”放在不同的“篮筐”里,Git就是 ** "鸡蛋 " + "篮筐" **。

既然 Git 是个软件,就先到 Git 官网针对你的操作系统安装对应的版本,博主是在 Windows10 下安装,在 Windows 下安装,可以一键next,安装后,右击鼠标会出现Git Bash HereGit GUI Here , 如下图所示:
在类 Unix 下的系统安装更简单,只要一行命令行即可,在 Debian 系的 Linux 系统下使用 sudo apt-get install git, 在 MacOS 下,使用 brew install git 其他平台安装可参考其他网站。

也许,你会觉得我在逗你玩,那不是有 GUI 吗?干嘛不用 GUI 却去用了命令行,是不是自讨苦吃啊!但是我说你不觉得用命令行整个逼格就高了吗?当然GUI确实入门比较快,如果你很排斥命令行的话,可自行搜索 Tortoise Git,这个我没有用过,但是身边有人用过,反映这个比Git自带的GUI友好些,如果你想更熟练地使用Git,那我还是建议你使用命令行,毕竟Git最初的设计就是在命令行下使用的。在后续只介绍Git的命令行操作。

对于Git的使用,现如今大部分 IDE 都提供相应的插件,使得Git的使用越来越方便,但通过命令行操作能够更深入理解 Git 的工作机制,就介绍一些常用的 Git 命令。对于命令行的使用,都会提供一个用户手册,不过不出意外的话一般都会提供英文版本的,英语好的话就可以直接阅读,如果英语不太好的话,也可以去网上查询中文的使用指南。

Git 常用本地命令

先介绍 Git 的第一个命令

1
git help

在终端敲好该命令后,按下回车,你会看到如下的显示:

可以看到help界面中把Git的操作分为5类,后续的文章会根据这个顺序来解释这些命令。可以看到这个help页面中,对于Git命令的分类为:

  1. 开始一个工作空间
  2. 对当前的工作空间进行操作
  3. 检查历史记录和状态
  4. 对历史记录的操作
  5. 合作

上述这些操作也是使用Git的一般过程:创建一个工作空间 \(\rightarrow\) 对该工作空间进行的操作 \(\rightarrow\) 操作的过程中会对历史记录进行操作 \(\rightarrow\) 共享该工作空间与他人合作。

现在继续介绍 git help 命令,如果你忘了某个命令的具体使用,比如clone这个命令,那么,你可以在控制台上输入 git help clone 之后你的浏览器就会显示出给命令的详细帮助手册(不需要联网,所有的帮助文档都在你的本地硬盘里),然而很可惜,还是英文的。 还是像上文说的那样,这种官方帮助文档,你可以不使用,但你要知道有这么一种东西,万一哪天情况很急,你又忘记了某一个命令的是有而且还没有其他的途径来获取帮助,这时候就可以通过官方提供的文档来解决你的问题。

接着我们来介绍一下开启一个工作空间的两种方法

从已有的项目直接复制一份过来,在此基础上进行后续的工作

1
git clone URL路径

比如在 GitHub 上要复制一个项目, 先该项目的主界面下,找到 Clone or download 按钮,然后复制提供的路径,对于开源的项目,提供的 HTTPS 还是 SSH 连接没有什么区别,对于私有的项目会有些许区别,在 HTTPS 的连接中,如果是私有的话,在对项目的提交过程中会提示你输入用户名和密码,使用 SSH 连接,则需要配置相应的 SSH Key 才可以进行访问。clone 操作如下图所示: 在终端输入

1
git clone https://github.com/GroverZhu/JSP-Servlet.git
之后就会在你的终端的目录下复制下该项目 这个命令用的好,代码写得少。身边的人,Git 用的不好,但这个命令记得可清楚了,一天完成 n 个项目不再是梦,别问怎么写的,问就是 git clone

从零开始创建一个工作空间

1
git init
选择一个目录,可以使用bash命令创建一个文件夹 mkdir tmp ,然后进入该文件夹 cd tmp/ ,再输入git init init 就是 initial 的缩写,即初始化,之后你可以进入文件夹 tmp 中查看,会有一个隐藏文件夹 .git ,这样就初始化好了,你就拥有一个 Git 工作空间了

介绍 Git 在本地分支的操作,首先通过 Bash 命令来创建一个 test 文件夹,在该文件夹下创建一个 a.txt

其实 Git 在 Windows 下的命令行终端里面是简化的 Bash Shell,如果你对 Linux 下的 Bash Shell 比较熟悉的话,你可以通过该终端进行相关的操作,不过一些命令还是不可以使用的,你可以到 GNU 下载相关的 package,进行相关配置,就可以像在 Linux 下运行相关命令。

先通过 git init 来初始化本地 Git 仓库,接着编辑a.txt

要在本地仓库提交的话,需要进行先运行 git add, 再进行 git commit。其中 git add 是将你当前的仓库内容提交到暂存区暂存区的话,你可以把它当作你去从家坐车到学校,那么车就是你从家到学校的暂存区,执行 git add 相当与你现在坐上车,再 git commit 之后才能到目的地即工作区 完整的命令如下:

1
2
git add 你要提交的文件名或文件夹名
git commit -m "提交信息"

此时你会发现无法提交,因为 Git 不知道你是谁,就像如果你座的车是动车的话,你得有身份证才能够买票就座,所以此时 Git 给出相应的提示,让你告诉Git你是谁。

1
2
git config --global user.email "你的邮箱地址"
git config --global user.name "你的名字"

登记自己的名字和邮箱之后,可以通过

1
2
git config user.name
git config user.email
来查看是否登记成功

再次进行 git commit,可以查看结果:

此时就提交成功,想想如果有 10 个文件要提交,那么你 add 的时候一定要打那么多的文件名吗?其实可以使用 git add --all 表示将当前的所有未提交或者被改变了的文件提交到暂存区里面。

这样的话,我们就要知道当前工作区里面是否有改变,就需要使用 git status 来查看当前目录下的文件是否发生变化。可以增加一个 b.txt 及修改 a.txt 里面的内容之后来看

由此可以看到,Git 是很智能的,他提示 a.txt 被修改,b.txt 未被跟踪,接着用 git addgit commit 提交

如果 git addgit commit 的次数多了,怎么知道之前的 commit 是什么?,可以使用 git log 来显示每一次的提交 这个偶尔会有可能中文显示不出来,可以使用下述命令行来显示中文

1
git config --global core.quotepath false
虽然 git log 这个命令行很有用,但是每次显示的太臃肿了,信息太多,我们需要一个比较简明的内容,这时候就需要考虑到强大的别名 alias

1
git config --global alias.logs "log --color --graph --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit"  

通过 logs 别名输出简明的 Git 日志。
Git 还提供打标签的功能,当你的项目完成到一定程度的时候,可以打个标签标记一下,使用 git tag 标签名,这样就算是打上一个标签了,可以使用 git tag,查看所有的标签,要切换到某一个标签的话,可以使用 git checkout 标签名

.gitignore 配置

在使用 Git 进行版本管理,有时候一些文件不需要提交,但使用 git status 命令后会出现未提示的文件,我们可以用 .gitignore 文件对不必要的文件进行屏蔽。

在Windows系统下进行配置 .gitignore 文件,确实有点难受。首先 Windows 操作系统下,直接右击鼠标无法新建一个不带文件名的文件,因此我们打开Git命令行,输入 touch .gitignore 命令你就可以在该文件夹下找到 .gitignore 文件(其实这是 Bash shell 下创建一个文件的命令,Git的命令行模式下是一种 shell,不信你可以在你的 Git 命令行模式下输入 Bash Shell的命令,它是可以运行,只不过命令没有那么全而已),建议用 VSCode或者其他文本编辑器编辑该文件。下面介绍 .gitignore 文件的编写:

.gitignore 中特殊符号

  1. "#" 相当于程序的注释的标记,"#" 后的内容都会被忽略掉;同时空行也会被忽略掉;
  2. "/" 表示目录,这个实际上是 Linux 下的目录表示,其中有绝对路径和相对路径的写法,绝对路径的意思是从一个头开始而这个头的表示为 /,例如在 Windows 下你的 C 盘里有一个 Windows 目录,那么表示该目录为 /c/Windows;相对的路径的意思为从当前目录开始表示为 ./ 开头,如果你已经在C盘,则上面目录的表示为 ./Windows
  3. "*" 为通配符,表示可以匹配任意多个字符;
  4. "?" 表示匹配任意单个字符;
  5. "[]" 表示单个字符的匹配列表;
  6. "!" 表示不忽略匹配到的文件或目录。

.gitignore 例子

  1. 忽略指定的文件,比如要忽略 readme.md,那么直接在 .gitignore 文件中编辑 readme.md 并保存,如要忽略所有后缀为 .md 的文件可以在 .gitignore 中编辑为 *.md*号出现表示在 .md 之前可以出现任意个字符(当文件名中有空格,要用 '' 包含起来如 'Program Files'/)
  2. 忽略指定文件夹,比如要忽略文件夹 bin,则在 .gitignore 文件编辑 bin/ ,如果是所有文件夹下都要有 bin 文件夹,并要忽略该文件可编写为 */bin/;
  3. 如果一个文件夹中你只需要其中的一两个,那么可以先忽略该文件夹,再用“!”提出需要的文件,例如你 bin 文件夹下,你只需要其中的 readme.md 文件,但它有十来个文件,此时 .gitignore 文件可编辑为:
1
2
bin/
!bin/readme.md

这样 .gitignore 文件就配置好了,不觉得很麻烦吗?其实早有人就提供相应的 .gitignore 配置文件,找到你要的部分,就可以直接拿来用,可在 gitignore 项目中查找对应的项目类型。在开启一个工程的时候,一定要去配置一下 .gitignore 文件,一个项目里面有部分文件是跟本地配置相关的,不应该添加到 Git 的管理中,不同的电脑,本地配置也会不一致,每个人都提交到 Git 中就会造成混乱。

Git 部分撤销操作命令

在使用 Git 的过程中,并不是每一次的add,commit都是你所预期要提交的,总有失手的时候,有可能你在add的时候你多加了个文件,或者commit之后你后悔了,觉得这次的提交不应该包含这么多的东西。Git的设计还是很友好的,让你有后悔的机会去改正。

介绍几个常见的情形:
1. 你在一次任务完成后,你要提交代码,使用 git add . 命令,在未使用 commit 命令之前,你觉得有一个文件现在提交太早了,那么,你可以使用 git rm --cached 文件名, 记得要加 --cached,表示是删除暂存区里的,如果直接使用 git rm 那么会把你本地的文件也删除掉。

  1. 如果你既 add,又 commit 了, 然后稍加思考,觉得事情不对,觉得刚才的 commit message 写得有问题, 那么请敲下 git commit --amend,然后就会跳到vi模式下,进行编辑你上一次的提交的信息。

如上图所示,你需要修改的就是那写黄体的字,黄体字下面是你上一次提交的信息。

  1. 如果你仔细思考,发现上一次提交的是什么鬼,决定全部删掉此次的提交重来,那么你有两个选择:
    • 使用 git reset 提交的标识号,先打印出你要回退的提交的标识号,使用 git log, 或者上一篇文章里提到的 git log --color --graph --pretty=format:'%Cred%h%Creset -%C(yellow)%d%Creset %s %Cgreen(%cr) %C(bold blue)<%an>%Creset' --abbrev-commit 当然正常人是不会去打这么一大长串的命令,正常的都配成别名alias, 比如,我要回退到下图中标记的提交,那么在控制台输入git reset 96a6128


      你可以通过这个命令回退到任何一个你需要的版本,但是在该提交之后的所有提交后都会没有,不过,当你的终端没有关闭,你可以找到之前的 log 中你最近提交的标识号,然后再用 git reset,如果只是想单纯看看那次的提交是什么,你可以使用 git checkout 提交的标识号, 这个命令会保持所有的提交不会被删除,你要回到当前分支的最新提交,就输入git checkout 分支名
    • 使用 git revert 提交的标识号, 这个是 Git 生成一个新的提交,这个的提交与你要回退的提交一模一样,比如你现在提交的分支是 a->b->c->d,但是现在你想回到 c ,现在你只需撤销d的提交就可以回到 c 的状态了,即输入命令git revert d,这样你的仓库状态就回到 c 状态。所以在版本控制中,更倾向与使用revert来回退版本,这样可以保留之前的所有信息。
  2. 如果你在编辑一个文件,突然发现,这还不如之前写得好,但是你又记不清你之前具体写的内容,你总不能一直用Ctrl + z,来撤销你的操作,一直回到最初状态,在 Git 中,用 git checkout 文件名,就可以恢复文件。
  3. 当然一般最难受的时候就是,在你开发一个新的功能的时候,有人跟你说之前的功能有问题,你需要去修改 bug,那你手头的工作还没保存下来,你也不能提交,这样会造成不必要的提交日志,你可以使用 git stash,将你目前的工作先存放起来,当你修改完 bug 后要回到你之前的工作,使用 git stash pop

Git 分支与远程命令

前面讲了那么多的Git操作,都是在同一个分支里面操作的,没有体现出来分布式的概念,那么 Git 的分布式是怎样的呢? Git 的分布式主要体现在分支(branch)上,那么下面就详细介绍 branch 的相关操作。

什么是分支,你可以看树杈,它有多个分支,Git 的分支也是这样的,一个主分支,可以有多个其他分支。在建立一个 Git 仓库的时候,你就在一个分支里面了,那个分支就是 master/main 分支,一般叫做主分支。

那么你要创建自己的分支可以使用 git branch 分支名, 创建你的分支,再通过 git checkout 分支名 来切换到你的分支。也可以使用 git checkout -b 分支名 直接新建并进入新的分支。

创建一个分支的话,是在你当前所在这个分支的基础上,创建一个跟你当前所在分支一模一样的分支,后续的修改之类的分支互不影响。

可以通过 git branch 查看当前项目的所有分支,前面带 * 号的就是当前所在的分支

如果有个分支不需要了,那么,使用 git branch -d 分支名 删除分支,如果有特殊情况,要强制删除掉某一分支,使用 git branch -D 分支名。切记不能在当前分支删除当前分支,必须切换到别的分支再执行删除操作。

与树杈不同的是,树杈一个分支分出去之后,就不会回来,但是Git的分支可以合并到任意一个分支。Git的合并是将一个分支合并到当前分支里面。一般有两种合并方式:
1. git merge 分支名,这个合并可以保留分支来源。
2. git rebases 分支名,将要合并的分支中新的内容直接加在当前分支后面,不会保留分支来源。

一般团队合作的话,使用 git merge 这样就可以追根溯源了,个人的话可以使用 git rebase,这样可以使提交记录更加简洁。

同时分支也会带来冲突问题,如果两个分支同时处理一个文件,那么就会产生冲突,需要我们手动解决。

有冲突的话,Git会有提示,会在分支名的后面标 MERGING

打开有冲突的文件,可以看到文件文件里面,Git都标出来了那边有冲突,<<<<<<< HEAD====== 表示当前分支在这个文件的修改,=======>>>>>>分支名 表示这个这个分支对这个文件的修改,根据需要修改冲突后,再使用 git addgit commit 的命令之后就可以了。

这样本地分支常用的操作就是这些了。剩下的就是远程的,远程的操作主要有:与远程主机创建连接,上传新的内容,从远程主机获取新的内容。与远程主机建立连接有两种协议:SSH 和 HTTPS,这两个具体协议的区别可以自己去查询,这里只介绍如何再这两种不同的协议建立连接。

首先,HTTPS的连接方式比较简单,只需要使用 git clone 地址连接,会让你输入账号和密码,在之后的提交中,可能你每次的提交到远程主机上都需要输入一次账号和密码,就显得有些麻烦了。

使用SSH协议,不过,你需要先生成SSH密钥,使用 ssh-keygen -t rsa -C 邮箱,邮箱一定是你在某一平台上的注册账号留下的邮箱。后面会有让你输入,直接按 'Enter' 键。上面会有生成密钥的文件目录。

之后去那个目录里面,会有一个 id_rsa.pub,打开此文件,将里面的内容粘贴到相应平台设置SSH的地方,这样远程主机就能识别出你使用的这台电脑了。

与远程主机建立联系的话,如果你是现在远程主机上建立的项目,本地是空的话,可以直接使用 git clone 把项目拷贝下来。如果是本地已经有一个项目了,要放在远程主机的话,现在远程主机上建立一个空的项目,然后使用 git remote add 远程主机名 远程链接,一般远程主机名使用origin,这样就建立好了远程联系了。

一般第一次提交的话,使用 git push -u origin master,后续的提交的话就可以直接用 git push 远程主机名 本地分支名,这个命令的完整格式是:git push 远程主机名 本地分支名:远程分支名,一般而言,远程分支名与本地分支名一致,这样便于管理。如果删除远程的一个分支的话,本地分支名就不用写了,即 git push 远程主机名 :远程分支名

从远程分支获取更新但不合并: git fetch 远程主机名 远程分支名
从远程分支获取更新并合并:git pull 远程主机名 远程分支名:本地分支名

上述就是Git分支的主要操作,相信你熟悉了这写操作之后就可以使用Git进行团队开发了。(注意命令中的:为英文的字符)

经过上面的讲解,Git 的基本操作就是这些,我也自己通过思维导图整理出来,供大家参考:

有需要的话,也可以进入在线预览

在此介绍的都是一些常用的 Git 命令,Git 是一个版本控制工具,工具的熟练程度一定是通过经常使用才熟悉的,所以一定要去找一个项目练练手。像基于 Git 的代码托管平台最有名气的就是GitHub,当然在国内的话,有coding, 码云等平台,可以入手一个动手实践一下。不过,如果想自己打一个代码托管平台,也是可以的,你可以自己买个VPS,在上面部署 Git 或者 GitLab,具体步骤可自已通过搜索引擎查找。

如果基础的 Git 命令已经掌握了,想进一步进阶的话,首推 Git 官网出版的 Git 说明书 Pro Git,如果平时忘记了 Git 的命令行的使用,还是到搜索引擎查找吧。