在使用Git前,我们需要先下载安装Git。目前,Git支持在Linux/Unix、Solaris、Mac以及Windows等平台上运行。Git下载地址
安装完成后,找到Git -> Git Bash
,打开它会出现一个命令行窗口,输入git --version
,如果成功显示版本,则表明Git安装成功。
由于Git是分布式版本控制系统,因此每个分支都要有自己的名称和邮箱,我们可以通过相关命令来进行名称和邮箱的配置。
git config --global user.name "Your Name" # 配置名称
git config --global user.email "[email protected]" # 配置邮箱
git config --list # 查看配置信息
git config user.name # 查看名称信息
git config user.email # 查看邮箱信息
--global
参数表示该分支上所有的Git仓库都会使用此配置,我们也可以对不同的仓库配置不同的名称和邮箱。
版本库又名仓库,英文名Repository,你可以简单的将它看成是一个目录,这个目录里面的所有文件都由Git进行管理,每个文件的修改、删除等操作,Git都可以跟踪到,便于任何时刻都可以追踪历史。
我们在siam这个目录中创建一个空目录mmf,然后通过git init
命令在mmf中创建Git仓库。
为了避免出现各种莫名其妙的问题,尽量不要在目录名中出现空格和中文。
mkdir mmf # 创建空目录mmf
cd mmf # 进入mmf
git init # 创建Git仓库
---------
Initialized empty Git repository in D:/siam/mmf/.git/
此时打开mmf目录,就会发现里面出现了一个.git
目录,这个目录就是Git用来跟踪和管理版本的版本库,千万不要随意修改和删除这个目录中的任意文件,否则很容易导致这个仓库出现问题。
首先要说明一点,所有的版本控制系统(包括Git),其实都只能跟踪到文本文件的改动,比如txt文件、网页、程序代码等。版本控制系统可以记录每一次的改动,比如在第5行添加了一个单词“linux”,在第八行删除了一个单词“windows”。而对于图片、视频等二进制文件,虽然也能由版本控制系统管理,但是却无法跟踪二进制文件的细致改动,只能把二进制文件串起来,也就是只知道图片或视频从100KB改成了200KB,但是到底改了什么,版本控制系统并不知道,也没办法知道。
另外,Microsoft的Word格式也是二进制的,因此版本控制系统是没法跟踪到Word文件的细致改动的。如果要真正的使用版本控制系统,就要以纯文本的方式编写文件。因为文本是有编码的,比如中文就有常用的GBK编码,这里强烈建议使用标准的UTF-8编码,所有语言使用同一种编码,既没有冲突,又被所有平台支持。
我们创建了一个文件readme.txt,并在文件中写入了一点内容,文件保存后需提交到本地Git版本库中。
touch readme.txt # 创建一个readme.txt文件
vim readme.txt # 使用vim编辑器打开文件
按i
键进入编辑模式,写入以下两行内容:
Git is a version control system.
Git is a free software.
按Esc
键退出编辑模式,按:
键进入末行模式,输入wq
并按回车,进行保存并退出,可以使用cat
命令查看文件内容:
cat readme.txt # 查看文件的内容
---------
Git is a version control system.
Git is a free software.
可以使用git status
命令查看当前的git状态:
git status # 查看git状态(新建了一个文件)
---------
On branch master
No commits yet
Untracked files:
(use "git add ..." to include in what will be committed)
readme.txt
nothing added to commit but untracked files present (use "git add" to track)
要将文件添加到版本库中,第一步需要通过git add
命令将文件添加到暂存区:
git add readme.txt # 将文件添加到暂存区
再查看一下git状态:
git status # 查看git状态(readme.txt被添加到暂存区)
---------
On branch master
No commits yet
Changes to be committed:
(use "git rm --cached ..." to unstage)
new file: readme.txt
第二步需要通过git commit
命令将文件提交到本地仓库:
git commit -m "write a readme.txt file" # 文件被提交至Git仓库
-m
后面跟的是本次提交的记录内容,这样写能够方便从历史记录中知道每一次改动的大概是什么。
为什么Git提交文件需要分两步呢?因为commit
可以一次性提交多个文件,因此我们可以多次add
不同的文件:
git add file1.txt
git add file2.txt file3.txt
git commit -m "add three files"
我们对readme.txt文件做一定修改,将之前的内容删除,并添加如下内容:
Git is a distributed version control system.
Git is a free software distributed under the GPL.
保存文件后,我们将其再次提交至本地版本库:
git add readme.txt
git commit -m "append GPL"
现在,本地版本库中一共有两个版本的readme.txt文件。在实际工作中,我们可以通过git log
命令来查看版本提交记录:
git log # 查看日志记录
---------
commit 4f489e74cdbcf902117a49fdf8c5f6a516ee2fb3 (HEAD -> master)
Author: aibc-hp <123456789@qq.com>
Date: Fri Aug 13 11:20:43 2023 +0800
append GPL
commit 0931364dad8d1a6601b4270a94418299f70f2de5
Author: aibc-hp <123456789@qq.com>
Date: Fri Aug 13 10:50:45 2023 +0800
write a readme.txt file
git log
命令能够显示从最近到最远的提交日志,我们可以看到有两次提交,第一次是write a readme.txt file,第二次是append GPL。我们看到的一串编号4f489e74cdbcf902117a49fdf8c5f6a516ee2fb3
是commit id(提交版本号)
,使用SHA1计算出的一个非常大的十六进制数,每个提交版本号都不会重复。
如果我们要将readme.txt文件回退到第一个版本,可以通过git reset
命令进行回退操作:
git reset --hard HEAD^
---------
HEAD is now at 0931364 write a readme.txt file
此时,查看一下readme.txt文件中的内容:
cat readme.txt
---------
Git is a version control system.
Git is a free software.
再查看一下日志记录,会发现最近的那个提交版本已经看不到了(只是看不到,并没有被删除):
git log
---------
commit 0931364dad8d1a6601b4270a94418299f70f2de5
Author: aibc-hp <123456789@qq.com>
Date: Fri Aug 13 10:50:45 2023 +0800
write a readme.txt file
如果我又想使用最近的那个版本怎么办呢?也有办法,只要我们知道那个版本的提交版本编号即可。如果包含提交版本编号的命令行窗口还没关闭,可以直接从窗口中去看,如果窗口已经关闭了,我们也可以通过git reflog
命令来显示每一次的操作记录,记录中就包含了提交版本编号:
git reflog
---------
0931364 HEAD@{1}: reset: moving to HEAD^
4f489e7 (HEAD -> master) HEAD@{2}: commit: append GPL
0931364 HEAD@{3}: commit (initial): write a readme.txt file
查看到提交版本编号之后,再通过git reset
命令进行版本切换:
git reset --hard 4f489e7
---------
HEAD is now at 4f489e7 append GPL
提交版本编号没必要写全,前7位就行,Git会自动去搜寻。
再查看一下日志记录,会发现最近的一次提交又出现了:
git log
---------
commit 4f489e74cdbcf902117a49fdf8c5f6a516ee2fb3 (HEAD -> master)
Author: aibc-hp <123456789@qq.com>
Date: Fri Aug 13 11:20:43 2023 +0800
append GPL
commit 0931364dad8d1a6601b4270a94418299f70f2de5
Author: aibc-hp <123456789@qq.com>
Date: Fri Aug 13 10:50:45 2023 +0800
write a readme.txt file
再查看一下readme.txt文件内容,发现已经变成了最近版本的内容:
cat readme.txt
---------
Git is a distributed version control system.
Git is a free software distributed under the GPL.
Git的版本回退(切换)速度非常快,因为Git的内部有一个指向当前版本的HEAD指针,当回退到第一个版本时,Git将HEAD指针指向了write a readme.txt file。
小结:
git log
命令查看提交记录,以便选择回退到哪个版本git reflog
命令查看操作记录,以便查看每个版本的提交版本编号,然后使用git reset --hard commit_id
命令进行版本切换。为什么说Git相较于其他版本控制系统更加优秀,其中一点是因为Git进行跟踪和管理的是修改,而非文件。那什么是修改呢?比如:
我们对readme.txt文件进行修改,添加两行新内容:
Git has a mutable index called stage.
Git tracks changes.
查看一下文件内容:
cat readme.txt
---------
Git is a distributed version control system.
Git is a free software distributed under the GPL.
Git has a mutable index called stage.
Git tracks changes.
将修改后的文件添加到版本库的暂存区:
git add readme.txt # 将文件添加到暂存区
git status # 查看版本库状态
---------
On branch master
Changes to be committed:
(use "git restore --staged ..." to unstage)
modified: readme.txt
此时,我们对readme.txt文件再做一次修改,将最后一行内容稍加改动:
Git is a distributed version control system.
Git is a free software distributed under the GPL.
Git has a mutable index called stage.
Git tracks changes of files.
这次改动的文件不添加到暂存区,我们直接使用git commit
命令提交到本地版本库:
git commit -m "git tracks changes"
---------
[master bf9deee] git tracks changes
1 file changed, 2 insertions(+)
查看一下状态:
git status
---------
On branch master
Changes not staged for commit:
(use "git add ..." to update what will be committed)
(use "git restore ..." to discard changes in working directory)
modified: readme.txt
no changes added to commit (use "git add" and/or "git commit -a")
通过状态信息会发现,我们明明提交了文件,却仍显示处于修改的状态,原因就是我们第二次修改的文件没有添加到暂存区,git commit
命令没有追踪到待提交的第二次修改内容。
我们可以通过git diff HEAD -- readme.txt
命令来对比此时工作区和Git版本库中的readme.txt文件的区别:
git diff HEAD -- readme.txt
---------
diff --git a/readme.txt b/readme.txt
index 76d770f..a9c5755 100644
--- a/readme.txt
+++ b/readme.txt
@@ -1,4 +1,4 @@
Git is a distributed version control system.
Git is a free software distributed under the GPL.
Git has a mutable index called stage.
-Git tracks changes.
+Git tracks changes of files.
可以发现,第二次的修改确实没有提交上去,就是因为第二次的修改没有添加到暂存区中。要使得每一次的修改都能提交至版本库,可以在每次修改后,将文件添加到暂存区,最后进行一次总的提交,方便又高效。
第一次修改 -> git add
-> 第二修改 -> git add
-> git commit
。
我们对readme.txt进行了修改,在文件最后添加了一行内容:
Git is a distributed version control system.
Git is a free software distributed under the GPL.
Git has a mutable index called stage.
Git tracks changes of files.
My stupid boss still prefers SVN.
文件保存后,正当我们想通过git add
命令将其添加到暂存区时,突然想起这句话不能让老板看到,否则会引起老板的不满,于是我们想撤销工作区的修改。我们可以先查看一下此时的状态:
git status
---------
On branch master
Changes not staged for commit:
(use "git add ..." to update what will be committed)
(use "git restore ..." to discard changes in working directory)
modified: readme.txt
no changes added to commit (use "git add" and/or "git commit -a")
我们可以发现,回答中已经告诉了我们如果不想接受此次修改,可以使用git restore file
命令来撤销工作区的修改:
git restore readme.txt # 撤销工作区中readme.txt文件的修改
git status
---------
On branch master
nothing to commit, working tree clean
查看一下当前文件内容,会发现确实已经撤销了修改:
cat readme.txt
---------
Git is a distributed version control system.
Git is a free software distributed under the GPL.
Git has a mutable index called stage.
Git tracks changes of files.
git restore readme.txt
命令的作用就是将readme.txt文件在工作区的修改全部撤销,前提是这些修改还没有添加到暂存区,也就是说这个撤销命令不能撤销已经添加到暂存区的内容。
假设刚才的修改我们已经将其添加到了暂存区,查看一下状态:
git add readme.txt # 添加到暂存区
git status # 查看状态
---------
On branch master
Changes to be committed:
(use "git restore --staged ..." to unstage)
modified: readme.txt
此时,我们想将暂存区的修改撤销该怎么办?我们可以通过git restore --staged file
命令来将文件的修改从暂存区撤销回工作区(工作区中还保留着修改):
git restore --staged readme.txt # 从将readme.txt文件的修改从暂存区撤回,退回到工作区状态
git status # 查看状态
---------
On branch master
Changes not staged for commit:
(use "git add ..." to update what will be committed)
(use "git restore ..." to discard changes in working directory)
modified: readme.txt
可以看到,当前的文件只是在工作区处于修改的状态,而没有添加到暂存区。
小结:
git restore readme.txt
git restore --staged readme.txt
git restore readme.txt
在Git中,删除也是一个修改操作。我们创建一个test.txt文件,并将其提交至本地版本库:
touch test.txt # 创建test.txt
git add test.txt # 添加到暂存区
git commit test.txt # 提交到仓库
此时,在工作区和仓库中都存在test.txt文件,它们是一模一样的。我们可以从工作区将文件删除:
rm test.txt # 只是删除工作区的test.txt文件
这个时候,Git知道你在工作区删除了文件,查看一下状态,git status
会告诉你哪些文件被删除了:
git status
---------
On branch master
Changes not staged for commit:
(use "git add/rm ..." to update what will be committed)
(use "git restore ..." to discard changes in working directory)
deleted: test.txt
no changes added to commit (use "git add" and/or "git commit -a")
可以看到,工作区中的test.txt文件已经被删除了,如果这时我们发现删错了,想把文件找回来该怎么办?没有问题,因为我们只是在工作区将test.txt删除了,而版本库中的test.txt文件仍然存在,我们可以通过git restore test.txt
命令撤回工作区的删除(修改)操作:
git restore test.txt # 撤回删除的test.txt文件
ls
---------
readme.txt test.txt
如果我们想同时删除工作区和版本库中的test.txt文件,可以通过git rm test.txt
命令来操作:
git rm test.txt # 同时删除工作区和版本库中的test.txt,此修改会被添加到暂存区
我们知道,删除也是一个修改操作,因此这个删除操作会被添加到暂存区,但此时版本库中的test.txt文件并没有被真正删除,我们还需要将这个删除事务提交至版本库:
git commit -m "del test.txt" # 提交删除事务
此时,工作区和版本库中的test.txt文件都被真正删除了,再使用撤回命令也撤回不了了。
注意: Git中的增、删、改都要经过暂存区,执行git rm test.txt
命令后,文件也只是被添加到了暂存区。如果想撤回删除,可使用git restore --staged test.txt
,工作区和版本库的test.txt都被恢复了。如果想继续删除,直接使用git commit
实现真正的删除。
小结:
rm file
git rm file
-> git commit
;git rm
和git add
都能将文件添加到暂存区;git rm file
-> git commit
命令的文件,使用版本回退命令git reset --hard commit_id
是可以恢复删除的文件的,只不过最近一次的提交会丢失,因为删除的就是最近的提交。Git常用的六个命令:
说明:
基础命令:
命令 | 说明 |
---|---|
git init | 初始化仓库 |
git clone | 拷贝一份远程仓库,也就是下载一个项目 |
git add | 添加文件到暂存区 |
git status | 查看仓库当前的状态,显示有变更的文件 |
git diff | 比较暂存区和版本库中文件的差异 |
git commit | 提交暂存区到本地仓库 |
git reset | 回退版本 |
git rm | 删除工作区和版本库中的文件 |
git mv | 移动或重命名工作区文件 |
git log | 查看历史提交记录 |
git reflog | 查看历史操作 |
git blame file | 以列表形式查看指定文件的历史修改记录 |
git remote | 远程仓库操作 |
git fetch | 从远程获取代码库 |
git pull | 拉取下载远程代码并合并 |
git push | 将本地代码上传至远程仓库并合并 |