天天看點

圖解 Git

<a target="_blank"></a>

圖解 Git

上面的四條指令在工作目錄、暫存目錄(也叫做索引)和倉庫之間複制檔案。

git add files 把目前檔案放入暫存區域。

git commit 給暫存區域生成快照并送出。

git reset -- files 用來撤銷最後一次git add files,你也可以用git reset 撤銷所有暫存區域檔案。

git checkout -- files 把檔案從暫存區域複制到工作目錄,用來丢棄本地修改。

你可以用 git reset -p, git checkout -p, or git add -p進入互動模式。

也可以跳過暫存區域直接從倉庫取出檔案或者直接送出代碼。

圖解 Git

git commit -a 相當于運作 git add 把所有目前目錄下的檔案加入暫存區域再運作。git commit.

git commit files 進行一次包含最後一次送出加上工作目錄中檔案快照的送出。并且檔案被添加到暫存區域。

git checkout head -- files 復原到複制最後一次送出。

後文中以下面的形式使用圖檔。

圖解 Git

綠色的5位字元表示送出的id,分别指向父節點。分支用橘色顯示,分别指向特定的送出。目前分支由附在其上的head辨別。 這張圖檔裡顯示最後5次送出,ed489是最新送出。 master分支指向此次送出,另一個maint分支指向祖父送出節點。

有許多種方法檢視兩次送出之間的變動。下面是一些示例。

圖解 Git

送出時,git用暫存區域的檔案建立一個新的送出,并把此時的節點設為父節點。然後把目前分支指向新的送出節點。下圖中,目前分支是master。 在運作指令之前,master指向ed489,送出後,master指向新的節點f0cec并以ed489作為父節點。

圖解 Git
圖解 Git

如果想更改一次送出,使用 git commit --amend。git會使用與目前送出相同的父節點進行一次新送出,舊的送出會被取消。

圖解 Git

checkout指令通常用來從倉庫中取出檔案,或者在分支中切換。

checkout指令讓git把檔案複制到工作目錄和暫存區域。比如git checkout head~ foo.c把檔案從foo.c送出節點head~ (目前送出節點的父節點)複制到工作目錄并且生成索引。注意目前分支沒有變化。

圖解 Git

如果沒有指定檔案名,而是一個本地分支,那麼将切換到那個分支去。同時把索引和工作目錄切換到那個分支對應的狀态。

圖解 Git
圖解 Git

head是分離的時候, 送出可以正常進行, 但是沒有更新已命名的分支. 。(可以看作是匿名分支。)

圖解 Git

如果此時切換到别的分支,那麼所作的工作會全部丢失。注意這個指令之後就不存在2eecb了。

圖解 Git

如果你想儲存目前的狀态,可以用這個指令建立一個新的分支: git checkout -b name。

圖解 Git

reset指令把目前分支指向另一個位置,并且有選擇的變動工作目錄和索引。也用來在從曆史倉庫中複制檔案到索引,而不動工作目錄。

如果不給選項,那麼目前分支指向到那個送出。如果用--hard選項,那麼工作目錄也更新,如果用--soft選項,那麼都不變。

圖解 Git

如果沒有給出送出點的版本号,那麼預設用head。這樣,分支指向不變,但是索引會復原到最後一次送出,如果用--hard選項,工作目錄也同樣。

圖解 Git
圖解 Git

merge 指令把不同分支合并起來。合并前,索引必須和目前送出相同。如果另一個分支是目前送出的祖父節點,那麼合并指令将什麼也不做。 另一種情況是如果目前送出是另一個分支的祖父節點,就導緻fast-forward合并。指向隻是簡單的移動,并生成一個新的送出。

圖解 Git
圖解 Git

cherry-pick指令"複制"一個送出節點并在目前複制做一次完全一樣的新送出。

圖解 Git
圖解 Git

上面的指令都在topic分支中進行,而不是master分支,在master分支上重演,并且把分支指向新的節點。注意舊送出沒有被引用,将被回收。

要限制復原範圍,使用--onto選項。下面的指令在master分支上重演目前分支從169a6以來的最近幾個送出,即2c33a。

圖解 Git

檔案内容并沒有真正存儲在索引(.git/index)或者送出對象中,而是以blob的形式分别存儲在資料庫中(.git/objects),并用sha-1值來校驗。 索引檔案用識别碼列出相關的blob檔案以及别的資料。對于送出來說,以樹(tree)的形式存儲,同樣用對于的哈希值識别。樹對應着工作目錄中的檔案夾,樹中包含的 樹或者blob對象對應着相應的子目錄和檔案。每次送出都存儲下它的上一級樹的識别碼。

如果用detached head送出,那麼最後一次送出會被the reflog for head引用。但是過一段時間就失效,最終被回收,與git commit --amend或者git rebase很像。

<b> 原文釋出時間為:2013-03-18</b>

<b>本文來自雲栖社群合作夥伴“linux中國”</b>