讓我們來看看輸出git show
。 (這是一個真正的回購實際輸出,雖然我會剪掉大部分位。)
$ git show d362e62
commit d362e62490dd7f59c170a0a050a203fa0eda9f5a
[snip]
diff --git a/fmt.py b/fmt.py
index c44c267..ba772ee 100755
[snip]
這裏,d362e62
是「短版」的承諾,即,它的SHA-1的真名。 「長」形式是完整的40個字符的版本,這是git show
輸出的第一行。
除了提交文本,提交本身含有「樹」(零個或多個「父母」)。我們可以git cat-file -p
看到:
$ git cat-file -p d362e62
tree 0b9bebfee8890b242875af0df209fd9f335bf14d
parent 41f3a6bcba1f5f7059133f862727809f49ff4657
[snip author, committer, and commit text]
我們可以看一下「樹」爲好。我可以使用上面的「真實名稱」SHA-1,但在這裏我使用了一些git語法:提交標識符^{tree}
告訴git從提交ID中提取樹ID。
$ git cat-file -p d362e62^{tree}
[snip]
120000 blob 7417b50d02819bbebeac0f4104850549935f7089 fmt
100755 blob ba772eeb6139de5a724d67d18ce01bfccaf57590 fmt.py
[snip]
我留在管道爲fmt
,因爲它是一個符號鏈接fmt.py
。符號鏈接的模式爲120000
,它告訴git blob
數據實際上是符號鏈接的目標。文件fmt.py
的模式爲100755
,它告訴git它是一個普通的文件並且它是可執行的(它是一個Python腳本)。 這是您在index
行中看到的100644
或100755
的來源。
團塊(文件對象)的「真名」在GIT回購是40個字符的SHA-1。 fmt.py
的7個字符的縮寫版本爲ba772ee
。 這是在上線index
兩個..
- 分隔號碼秒數。
在該行的第一號是「真名」中的以前版本的文件,Git的回購即,fmt.py
那是在回購之前的版本,我創建提交d362e62
。
我們可以使用特殊的git語法的另一位看到這些孩子的。 作爲記錄在gitrevisions,之後提交說明符的帽子字符(抑揚,向上箭頭,不管你喜歡稱呼它)^
告訴混帳找到犯下的第一個父。所以:
$ git rev-parse d362e62^
41f3a6bcba1f5f7059133f862727809f49ff4657
告訴我們承諾提交之前我給git show
是一個名爲41f3a6b...
。而且,果然,如果我們git cat-file -p
,我們得到另一個犯了另一棵樹,如果我們git cat-file
那棵樹-ID,並查找fmt.py
我們會發現另一個blob
與另一SHA-1:
$ git cat-file -p 41f3a6b
tree cbfb63beec96eebf0c73ba6a501cc8151adfec8a
parent 80eeb496ea3f538aa14acdc6b0815024a5e99c7e
[snip]
$ git cat-file -p cbfb63beec96eebf0c73ba6a501cc8151adfec8a | grep fmt.py
100755 blob c44c267c4603838ac7a54aa450b33d0dd7a8bebc fmt.py
$
還有它是:cc4c267
是存儲在之前的提交中的文件的「真實名稱」的縮寫形式。 這是行中的第一個號碼。
我把這一切全部寫出來以說明git如何從「A點」到「B點」。但是,就像用短手語法d362e62^{tree}
,有一個很簡單的方法來獲取BLOB使用git rev-parse
SHA-1的值:
$ git rev-parse d362e62:fmt.py
ba772eeb6139de5a724d67d18ce01bfccaf57590
$ git rev-parse d362e62^:fmt.py
c44c267c4603838ac7a54aa450b33d0dd7a8bebc
如果你想縮短的版本,使用git rev-parse --short
截斷SHA- 1值爲(通常)7個字符。
所以:
而且我想知道哪些commit
產生的補丁,以及如何解析的補丁15 index e220f68..e611b24 100644
?
的15
是行號你(或有人的地方)加入,現在你知道什麼是價值觀上的index
線其餘都是。但是要找到提交-這很困難。 提交是發現其他值。沒有將「其他值」鏈接回「提交」:「箭頭」只是指向提交到樹,然後從樹到斑點。沒有從斑點到樹的指針,也沒有從樹到提交的指針。
Git總是以某種外部指定名稱開始。通常這是一個分支名稱或標籤,或者是一個「符號參考」(通常是HEAD
,如果沒有「分離頭」)。該引用查找提交。 如果引用是分支名稱,則該提交是該分支的「提示」。 如果它是一個標籤,它仍然會發現一個提交。如果是HEAD
和HEAD
是master
之類的分支的名稱,git只是將HEAD
轉換爲master
,然後將master
轉換爲提交。換句話說,提交是您開始的地方,通常是從名稱到提交ID,但您幾乎總是可以在此指定一個「原始」SHA-1 ID。
一旦git有一個提交ID,該提交標識更多的提交(它的父母)和一棵樹。如果需要,該樹標識子樹,並且該樹及其子樹標識斑點。從具有「外部名稱」的所有提交開始,git最終會查找所有樹和所有blob,並且存儲庫中的所有樹或Blob都是而不是,如果以這種方式發現,則可以使用git gc
(或當git gc
自動運行)。 (這是如何刪除分支,以及git在內部創建的任何數量的特殊臨時文件,都會在稍後進行清理。)
Git有特殊語法的很多。最有用的記憶,在我看來:以後的事情=父
- 帽子:
master^
=
- 波浪 「
master
的父母」 和編號N
之後的事情=備份N
父母:master~2
= 「的master
祖父母」
X..Y
=「由Y
選擇所有修訂,但不包括所有版本選擇由X
「:git log master..devel
=‘登錄分支devel
所有提交使不上master
’
的..
語法也用於git diff
,但在這裏,而不是」東西上Y
這不是X
「,您可以直接比較與X
相關的版本與Y
相關的版本。
我故意跳過「帶註釋的標籤」,它也有存儲庫實體。在某些情況下,git將訪問標籤對象,而在其他情況下 - 當需要提交時,樹和/或blob-git將自動跟隨帶註釋的標籤。在內部,註釋標籤看起來與提交非常相似,除了代替樹和父項外,它具有對另一個git存儲庫對象的引用 - 通常直接指向提交,但有時指向另一個標籤,理論上可以創建爲樹或blob註釋標記,完全跳過提交部分。
分支名稱始終指向其自己分支的尖端,但該分支可能只是另一分支的一部分。舉例來說,假設你有提交的一個很好的線性序列:
...<-- C3 <-- C4 <-- C5 <-- C6 <-- C7
其中C7擁有C6作爲其母公司,C6有C5,等等。如果分支標籤X
是對提交C5
的引用,則分支X在C5處結束。如果分支標籤Y
指向C7,則分支Y在C7處結束。在這種情況下,分支Y「包含」分支X,但反之亦然。