本來地址:git乾貨系列:(二)深刻學習以前先理解git暫存區
博客地址:tengj.top/git
暫存區(stage, index)
是Git
最重要的概念之一,理解了這個概念不少 Git
命令就再也不那麼神祕了。下面幾個驗證例子一開始看不懂不要緊,工做區、版本庫中的暫存區和版本庫之間的關係圖先理解先。緩存
下面這個圖展現了工做區、版本庫中的暫存區和版本庫之間的關係。
bash
Git
命令是如何影響工做區和暫存區
(stage, index)
的。
index
的區域是暫存區(stage, index)
,標記爲 master
的是 master
分支所表明的目錄樹。HEAD
實際是指向master
分支的一個「遊標」。因此圖示的命令中出現HEAD
的地方能夠用master
來替換。objects
標識的區域爲Git
的對象庫,實際位於.git/objects
目錄下,咱們會在後面的章節重點介紹。git add
命令時,暫存區的目錄樹被更新,同時工做區修改(或新增)的文件內容被寫入到對象庫中的一個新的對象中,而該對象的ID
被記錄在暫存區的文件索引中。(git commit)
時,暫存區的目錄樹寫到版本庫(對象庫)中,master
分支會作相應的更新。即master
指向的目錄樹就是提交時暫存區的目錄樹。git reset HEAD
命令時,暫存區的目錄樹會被重寫,被 master 分支指向的目錄樹所替換,可是工做區不受影響。git checkout .
或者 git checkout -- [file]
命令時,會用暫存區所有或指定的文件替換工做區的文件。這個操做很危險,會清除工做區中未添加到暫存區的改動。git checkout HEAD .
或者 git checkout HEAD [file]
命令時,會用 HEAD
指向的 master
分支中的所有或者部分文件替換暫存區和以及工做區中的文件。這個命令也是極具危險性的,由於不但會清除工做區中未提交的改動,也會清除暫存區中未提交的改 動。git rm --cached [file]
命令時,會直接從暫存區刪除文件,工做區則不作出改變。git rm file
命令時,會同時刪除暫存區和工做區的文件。rm file
命令時,只會刪除工做區的文件。假設:
工做區:a
暫存區(index):b
HEAD:C學習
git diff命令結論spa
git diff 比較a跟b
git diff --cached 比較b跟c
git diff HEAD 比較a跟c複製代碼
git reset跟 git checkout結論3d
git reset HEAD c覆蓋b
git checkout -- <file> b覆蓋a
git checkout HEAD <file> c覆蓋a,b複製代碼
git rm命令結論code
git rm 刪除a跟b
git rm --cached 只刪除b
rm file 只刪除a複製代碼
例子,默認新建一個readme.txt
,裏面輸入內容one
而後add而且commit
一次。cdn
1:修改readme.txt
,新增內容two
,這時候a內容改變了,多了two
,而b跟c內容不變,都只有one
。
執行git diff readme.txt
查看效果 xml
結論:如圖看出,內容有修改, a跟b比較了對象
執行git diff --cached readme.txt
查看效果
結論:如圖看出,沒有變化,由於b跟c內容同樣。
執行git diff HEAD readme.txt
查看效果
如圖所示:內容有修改,a跟c比較了
2.這時候執行git add readme.txt
,這時候a,b內容都多了two,而c內容不變,只有one
執行git diff readme.txt
查看效果
結論:如圖看出,沒有變化, 由於a跟b內容同樣。
執行git diff --cached readme.txt查看效果
結論:如圖看出,內容有修改,b跟c比較了
執行git diff HEAD readme.txt
查看效果
結論:如圖看出,內容有修改,a跟c比較了
3.最後使用git commit
提交一次,這時候a,b,c內容都同樣,都包含two
。
結論,如圖看出,沒有變化,說明a,b,c內容同樣
根據上面的實例再一次證實了以下觀點:
git diff 比較工做區跟暫存區
git diff --cached 比較暫存區跟HEAD
git diff HEAD 比較工做區跟HEAD複製代碼
例子,默認新建一個readme.txt
,裏面輸入內容one
而後add而且commit
一次,這時候a,b,c內容都是one
1.修改readme.txt
,新增內容two
,執行git add readme.txt
操做,這時候a ,b內容都多了two
,c仍是隻有one
.
執行git reset HEAD -- readme.txt
命令後,c覆蓋b,這時候b內容也變成只有one
了,使用git diff readme.txt
命令能夠看到,有內容修改,a跟b內容不同。
2.此時a內容有two,b和c都只有one,執行git checkout -- readme.txt
後,b覆蓋a,此時a,b,c都是one。執行git diff readme.txt
命令能夠看到,沒有改變。
3.此時a,b,c都只有one
,修改一下,添加內容two
,執行git add readme.txt
和git commit -m "two"
.再修改一次readme.txt
,添加內容three
,而後會執行git add readme.txt
,此時a跟b都包含three,而c只包含one跟two。執行git checkout HEAD readme.txt
後,c覆蓋a和b,a,b裏面內容都只有one跟two。分別使用命令git diff --cached
和git diff HEAD
來查看b跟c,a跟c的比對,發現都同樣。
根據上面的實例再一次證實了以下觀點:
git reset HEAD HEAD覆蓋暫存區
git checkout -- <file> 暫存區覆蓋工做區
git checkout HEAD <file> HEAD覆蓋暫存區和工做區複製代碼
默認新建一個readme.txt
,裏面輸入內容one
,而後使用git add readme.txt
命令。
1.執行git rm readme.txt命令,發現文件被刪除了。
2.再新建一個一個readme.txt
,裏面輸入內容 one,而後使用git add readme.txt
命令。執行git rm --cached readme.txt
命令,發現文件內readme.txt
還在,而後執行git status
命令,發現是Untracked
狀態,也就是未add
,這就說明暫存區被刪除了。
根據上面的實例再一次證實了以下觀點:
git rm file 會將文件從緩存區和你的硬盤中(工做區)刪除
git rm --cached 只刪除暫存區,不刪除工做區
rm file 只刪除工做區複製代碼
暫存區的原理須要你們重複的加深瞭解,基礎打牢了後面學起來就輕鬆不少,上面幾個例子都本身驗證一遍,加深印象。
一直以爲本身寫的不是技術,而是情懷,一篇篇文章是本身這一路走來的痕跡。靠專業技能的成功是最具可複製性的,但願個人這條路能讓你少走彎路,但願我能幫你抹去知識的蒙塵,但願我能幫你理清知識的脈絡,但願將來技術之巔上有你也有我。