今天小铭酱带大家探索一下git的奥秘!

1.初步探索

首先我在一个空的文件夹新建了一个名叫hello.html文件,文件内容只有一句话“hello git”。我们先引入git,看看git能为我们它能干什么,嘻嘻~





1) git init

初始化后,在当前目录下会出现一个名为 .git 的目录,所有 Git 需要的数据和资源都存放在这个目录中。就这么简单,我们已经有一个代码仓库了。



2) git add

有了仓库,那第二部我们要让git知道哪些文件需要被管理或跟踪的。输入"git add ." (这里.是代表所有文件,也可以输具体文件名)
让当前所有文件都被git跟踪到。

3) git commit

add后我们需要第一次commit,这样git才会帮我们创建一个主分支,什么是分支后面会讲。我们先输入"git commit -m "init
commit" 这里-m必须加,表示这次提交的描述,内容我们随意输,主要是给自己做标记用的。



4) git log

试试输入git
log,我们发现我们的提交已经被记录下来了。就这样一个最基本简单的流程已经走完了。哎呀,妈呀,这git到底有啥用?我咋完全不懂呢?别急,我们看看神奇的事情开始发生了。

 

 

2.进入git的世界

1) git checkout

这时粗心的我不小心把hello文件中的代码给误删了,而且我又忘了代码写些什么来着~~~咋办尼?



嘿嘿,这时git闪亮登场。试试输入"git checkout hello.html"看看会怎样。




咦!我们发现那句代码神奇的又回来了。难道这个命令是可以把我现在的代码还原到上次提交的吗?好像没那么简单,不过我们也暂时这样理解吧,稍后会详细介绍。这下我会玩了,我可以随便修改代码,如果错了,直接checkout不就行了吗,哈哈。

2) git status

这时我们继续编辑代码,当代码敲得差不多时,咦~ 我到底改了什么呢?输入"git status",我们看到以下信息,它告诉我们hello.html文件被修改了。



大家肯定跟我一样,那到底这个文件修改了哪些内容呢?不急,这"git
status"只是列了个大概,告诉你有哪些文件被修改过,但如果想知道具体内容,就要借助git diff命令。

3)git diff

输入"git diff"这里显示了详细的修改。



ok,查看了修改内容,觉得没问题,那就提交吧。输入“git add ." 
等等,我好像发现了个问题。为什么git要先add然后再commit呢?干嘛不直接commit要多一部这么麻烦呢?这里就涉及git的设计了。

3.git 你到底是啥构造?

1)理解git构造

首先我们先来理解以下git的概念

* 工作区:就是你在电脑看到的目录
* 暂存区:英文叫stage或index
* 版本库:工作区隐藏目录.git
* 分支:一连串提交组成了一个分支


 


这里借用w3c的图给大家看,当我们编辑完代码,然后准备提交。当我们add时候,其实是把我们工作区的代码放到了暂存区了。然后当我们commit时候,才是真的写到分支上了。分支是什么呢?分支就相当于把我们每一次提交串连成一条时间轴。而这条时间轴就相当于一个分支,哦~
这样大概理解了。至于为什么要搞一个暂存区,是因为中间有了缓冲,使得管理代码更具有灵活性了。

2)重温git status 和 git diff 和 git checkout

现在,我们新建一个html文件,取名heihei。输入"git add
heihei.html"让git跟踪这个文件。同时这时我们修改一下hello.html文件(注意,hello文件没有现在是没执行add)。这时试试status一下会怎样?



这下我好像看懂了,哈哈。那再试试diff命令?




Yoshi(日文)原来这是默认查看工作区和暂存区之间的差异变化,也就是修改之后还没暂存起来的变化内容。那我要看暂存区和上次提交的详细变化该怎么看呢?输入"git
diff --staged"



Yoshi 原来是这样子 哈哈 好简单是吧~
就是这么简单,不过这只是最基本的操作,我们再看看checkout命令,这时候先忽略掉heihei文件,把hello文件add一下,再给hello文件添加一句代码。



现在工作区,暂存区,分支上的代码分别是这样的




好,现在三个地方的代码都不一样,这时候我们执行checkout命令会怎样呢?我们知道checkout是把工作区修改的代码删去,那它是根据暂存区的呢还是分支上的呢?



输入命令checkout,我们发现竟然回到了暂存区的代码。噢~
这下我懂了,原来checkout是回退到暂存区的代码。这下好玩了,我可以随便敲代码,然后把确定的代码放到暂存区,一出问题,就checkout回退到暂存区的就可以了。这时候有孩童又想问了,那如何回退分支上的代码尼?

3) git checkout head

 现在工作区,暂存区,分支上刚刚上面的一样

  

输入 “git checkout head" 看看会怎么样?




这时候,惊奇的发现暂存区和工作区都被分支上的代码重写了,也就是说工作区回退到分支上的代码,暂存区也被清空。(意味着你工作区和暂存区新修改的代码都没了)所以这个命令是极具危险性的,一定要小心使用哦~

4) git reset命令

当你玩转工作区,暂存区,分支三地的代码时,也许你还不满足。感觉git应该有更强大的功能,我们现在就看看git reset命令到底是个啥东西。git
reset命令主要有三个可选参数,分别是git reset --soft,git reset --mixed,git reset
--hard,它们的危险性也是逐步增大的,下面我们详细看一下。现在的代码是这样子:



现在我们再修改一下代码,并提交。标记名称 "test get reset"。



现在我们输入"git reset --soft 3d542d6e307e067e7b281de74d328d6114084d04"
看看会怎么样?后面那串(3d....)是 "beautiful girl" 那次提交的id。 我们log一下,发觉最新的一次提交不见了。



status和diff看看?



不知道大家看懂没,我们发现git reset --soft命令竟然把最近一次提交 "倒回到" 未提交的状态,所有改变都回到了暂存区放着,哈哈,原来如此~
那这个有什么用呢?比如我们提交了后,誒~发现漏了点东西,那我们就可以用git reset
--soft(别忘了加上上一次提交的id)回退到我们未提交的状态,然后修改重新提交。Ok,很好用~。下面再看看git reset
mixed,这是不带参数的默认选项。我们把刚刚reset --soft回滚的再次提交,取名"text reset mixed"



输入 "git reset mixed 3d542d6e307e067e7b281de74d328d6114084d04" 或 "git reset
3d542d6e307e067e7b281de74d328d6114084d04" 。




这个神奇了,我们发现最近的一次提交记录没有了(注意上图中我忘记log一下给大家看了),暂存区没有变化,上一次提交的修改都回到了工作区(红色字体代表工作区的修改,也就是没执行add)。

git reset
hard这里就不演示了,相信大家也能猜到到结果,就是最近一次提交的修改不是回到暂存区,也不是回到工作区,而是完全丢失了,所以这个操作是最危险的,一定要小心使用。到这里小铭酱就有点不明白了,git
reset好像都不是针对上一次提交回退代码的,而是针对上上一次进行回滚操作的,噢~
对了,假如我工作区的代码胡乱写了一番,暂存区的没有任何修改,那我直接checkout不就相当于回退到上一个版本了吗?那如果这时暂存区里面已经有东西了,那该如何回到上一个版本呢?我们可以用checkoutout
head是吧。好~ 这下大概懂了。

总结一下:

* git reset --soft 加上(上上一次commit的id),那么上一次提交会消失,回到没提交状态,所有修改放在暂存区里
* git reset --mixed 加上(上上一次commit的id),那么上一次提交同样消失,所有修改回放到工作区里
* git reset --hard 
加上(上上一次commit的id),那么上一次提交"永久"消失,上一次提交数据就完全没了,代码完全回到上上一次提交的版本
说到这里,也感叹git的设计好厉害,好吧~ 这部分先到此为止,下面又更好玩的 ——分支

4.玩转git分支

1)git branch (branchname)

我们输入"git branch two" 创建一个名为two的分支



2)git checkout (branchname)

输入"git checkout two" 切换到two分支



3) git branch

列出所有分支,妈呀,这个到底咋玩?别急,我们先切换到主分支上,现在我们修改代码,看下面hello.html的改动





我们把修改的提交了,命名为"test branch",好~ 神奇的事情出现了,我们切回分支two,log一下



发现在分支two上,根本没有"test branch"提交,这说明现在代码已经在两条线上开发啦~
我们再在分支two上作一些修改,并且同样是修改hello.html文件看看会怎样?同时我们画个图看看。



 



相信聪明的小伙伴们都知道这是有啥用,这里不多说了,我这里是想跟大家探究一下合并分支的问题,来~ 一起看一下。

4)git merge

切换到主分支,输入“git merge two"





哇草,既然冲突了~
哈哈,当我们两个分支都同时修改了同一个文件,合并时就会出现冲突,这时候我们就需要手动修改一下,然后重新提交,便能把分支上改的东东合并我主分支上啦~



 最后,感谢大家和小铭酱畅游了一遍git的世界,第一次写,写得不是很好,哈哈~ 在后续中小铭酱将会跟大家继续发掘git的好玩之处,谢谢大家!