【Git】工作區、暫存區與版本庫
本篇博文旨在介紹git的工作區,暫存區和版本庫的概念;並說明使用git add、git commit 等指令時,對工作區,暫存區以及版本庫分別造成的結果;
對於會使用git的人,git add,git commit,git checkout ,git reset這些指令應該很熟悉了
我們一般使用git,修改好檔案後,會用git add 檔名,git commit -m 備註這兩條指令,然而他們的作用是什麼呢?為什麼不一條指令直接就OK了?
關於為什麼需要暫存區,我們在文章末尾解答
工作區、暫存區以及版本庫的概念
工作區(Working directory)
將一個資料夾通過git init 設定成一個git可以管理的資料夾時,這個資料夾裡的內容就是工作區
版本庫(repository)
當工作區生成後(git init),在Linux下用 ls -a 檢視可以發現
除了 . / ../ 還有個 .git
這個 .git 就是版本庫
注意:工作區是除了版本庫之外的其他內容
暫存區(stage / index)
暫存區,叫stage 或者 index ,是用來暫時存放工作區中修改的內容;
可以理解為一箇中轉站
通過下圖來深入理解工作區、暫存區和版本庫
細心觀察上圖的童鞋會發現,除了工作區,暫存區,版本庫,還有個東西就是object和master
什麼是object
object是git物件庫,是用來儲存各種建立的物件以及內容
什麼是master
master我們也經常用到,它是我們的主分支
當我們git init後,並不會立刻產生分支
而是我們添加了一個檔案,並git add,gitcommit後
這時我們檢視分支情況
便可以看到master分支了
並且悄悄告訴你,分支都存在在.git/head/refs目錄下
什麼是HEAD
HEAD是一個引用,引用的是當前的分支
如果當前處於master分支,那麼HEAD就會指向master
如果當前切換到Dev分支或者其他分支。那麼HEAd就會指向該分支
幾個對三個區造成影響的指令
1、git add
當我們使用git add 指令時,就是將對應修改的檔案新增到暫存區中
這時,暫存區中的目錄樹被更新
2、git commit
緊接著,我們使用git commit指令,便會將暫存區中做出的修改提交到版本庫中
這時master指向的分支被更新
3、git reset HEAD
當使用git reset HEAD 指令時,暫存區的內容會被版本庫的內容覆蓋
4、git checkout --file
使用git checkout --file時,是將工作區指定修改的檔案被暫存區的內容覆蓋(消除所有工作區進行的改動),這個動作很危險
git checkout . 也是如此,該指令是將所有修改的檔案被暫存區的內容覆蓋
5、git rm --cached
使用git rm --cached file時,直接從暫存區進行檔案的刪除,不會影響工作區的內容
6、git checkout HEAD --file
git checkout HEAD --flie 時,會將版本庫中的對應的檔案內容直接替換工作區和暫存區中的該檔案
這個動作也是危險的,同樣git checkout HEAD . 是將所有的內容替換工作區和暫存區的檔案
如何檢視三個分割槽的區別
git diff 檢視工作區和暫存區的區別
git diff --cached 檢視暫存區和版本庫之間的區別
git diff HEAD 檢視工作區和版本庫之間的區別
git status 檢視當前的工作狀態
為什麼需要暫存區
假設一個場景:
當你自己工作時,寫檔案寫了一半,沒有commit交給版本庫時
突然上司告訴你有一個Bug要緊急處理,但是完成自己的工作還需要兩天時間
這時,你不能commit提交給版本庫,因為你沒做完,這樣會影響到其他人的工作
試想:
如果沒有暫存區,你修改的檔案只可以立刻儲存到版本庫中,這樣很容易對別人的工作造成影響
所以我們需要暫存區
上述場景解決步驟
1、利用git stash將自己的工作隱藏
2、新建一個bug分支來處理bug
3、處理完後,利用stash pop將隱藏的檔案彈出
4、繼續工作