Git Step by Step (5):Git分支(branch)

jopen 9年前發布 | 17K 次閱讀 Git 版本控制系統

原文出處: 田小計劃的博客  

在前面兩篇文章中介紹了Git的基本原理,都是理論知識。這篇文章我們再次回到實踐中,看看Git分支(branch)的使用。

在代碼版本控制工具中,都會有branch的概念。剛開始建立版本倉庫的時候,我們只有一個主分支(master branch),我們不可能把日常的新功能開發、代碼優化以及bug修復等概念工作全都放在主分支上,這樣會使主分支很難維護。這就是為什么會有branch。

分支的創建及刪除

分支的創建

在Git中,branch的創建很簡單,我們可以通過下面的命令創建一個”release-1.0″的branch。

然后通過”checkout”命令來切換branch。

 Git Step by Step (4):探索.git目錄

在Git中,我們可以通過”git checkout -b”命令來達到同時創建并切換branch的效果。

注意:大家一定還記得第二篇文章中我們通過”checkout”命令來還原WorkSpace中的更新,在還原的命令中我們使用的是”checkout –”,如果沒有”–”就代表切換branch。

根據前面兩篇文章的知識,我們進入”.git/refs/heads”目錄,發現有”HEAD”和”release-1.0″兩個文件,并且兩個文件包含的哈希值相同,根據”git log”可以知道這個哈希值代表master上最新的提交。所以,創建分支后我們會得到下面的關系圖,從值張圖中可以看到,branch的切換對應HEAD引用值的改變。

 Git Step by Step (4):探索.git目錄

有了新的branch之后,我們就可以分別在不同的branch上工作了。假設我們現在更新”app.py”,并且在release-1.0 branch上面提交,重新查看對象關系圖。

 Git Step by Step (4):探索.git目錄

根據上面的對象圖,可以分析出以下信息:

  • “ref/heads/release-1.0″文件內的哈希值將更新為release-1.0 branch上最新的更新
  • release-1.0 branch上面的更新不會體現在master branch

經過查看,”ref/heads/release-1.0″文件的內容確實是release-1.0 branch上最新的更新。并且,當我們切換到master branch的時候,所有master上的東西都沒有變化。

分支的刪除

分支的刪除比較簡單,可以使用”git branch -d”命令,為了不影響后面的內容,這里演示新建、刪除dev branch。

 Git Step by Step (4):探索.git目錄

分支的合并

branch的創建是為了方便開發、修復bug以及保持master的穩定。但是最終branch上的內容還是要合并到master的,接下來就看看分支的合并。

在Git中,可以通過”Git merge”來合并分支,繼續前面的例子,我們可以把”app.py”的更新merge到master branch上。

 Git Step by Step (4):探索.git目錄

這時候,master的HEAD就被更新了,跟release-1.0內容一致了,這些就是merge命令做的事情。

 Git Step by Step (4):探索.git目錄

合并沖突

在branch的合并中,很多時候我們會遇到沖突,那么我們就需要手動解決沖突,然后再提交了。

為了演示沖突合并,我們回退master到上一次提交(一定還記得git reset吧),然后同樣更新”app.py”提交到master。

 Git Step by Step (4):探索.git目錄

通過上面可以看到,master和release-1.0上同時修改了”app.py”,合并時引起了沖突。在Git中,會用”<<<<<<<”,”=======”,”>>>>>>>”標記出沖突區域,我們需要根據這些符號找到所有的沖突并解決。

 Git Step by Step (4):探索.git目錄

沖突解決之后,我們通過”git log”來產看一些結果,但是這次我們要給”git log”加一些參數。

 Git Step by Step (4):探索.git目錄

同時,這里給出最新的對象關系圖

 Git Step by Step (4):探索.git目錄

branch相關操作

在branch的使用過程中,我們還會經常使用到stash和diff操作,下面分別進行介紹。

stash

在Git中,stash是個很有用的命令,可以保存我們做到一半的工作,可以理解成一個未完成工作的保存區。

假如我們在release-1.0 branch做了一些更新,但是想做的事情還沒有全部完成,不能提交,這是我們又要切換到master branch,這是Git會禁止branch切換。

比如,例子中我們從app.py中刪除”div(16, 4)”。

 Git Step by Step (4):探索.git目錄

這個時候我們就需要使用stash來保存未完成的工作了。

 Git Step by Step (4):探索.git目錄

如果需要繼續前面的工作,我們可以通過”git stash apply”來還原被保存的工作狀態。

 Git Step by Step (4):探索.git目錄

stash空間就像是一個棧空間,每次通過stash保存等內容都會被壓入stash棧。命令不僅僅是支持簡單的list、apply操作,接下來我們看看更多的stash命令。

  1. git stash save:可以通過自定義的信息來描述一個stash

     Git Step by Step (4):探索.git目錄

  2. git stash apply stash@{n}:通過這個命令,我們可以選擇stash棧中的stash,從而恢復到特定的狀態;”git stash apply”使用棧頂來還原WorkSpace。
  3. git stash pop:就像”git stash apply”使用棧頂來還原WorkSpace,但是同時會從stash棧中刪除當前的棧頂stash。

stash工作原理

相信大家都看到了stash的強大,下面我們來看看stash的工作原理。在使用過stash保存之后,我們會發現.git目錄中出現了兩個新文件”.git/refs/stash”和”.git/logs/refs/stash”。兩個文件內容分別如下:

.git/refs/stash

dcac98e565864edc6f636b08660baebe2c97e7d2

.git/logs/refs/stash

0000000000000000000000000000000000000000 dcac98e565864edc6f636b08660baebe2c97e7d2 WilberTian <Wilber***com> 1420201804 +0800    WIP on release-1.0: ed17809 update app.py on release branch

根據我們在對象關系模型那篇文章中學到的內容,我們可以得到以下信息,所以可以看到,stash存放內容也是可以根據對象關系模型一點點找出來。

這里就不提供對象關系圖了,比較復雜,有興趣的同學可以自己畫一個看看各個對象之間的關系。

 Git Step by Step (4):探索.git目錄

branch之間的diff

在前面的文章中我們通過diff比較過同一個分支上的內容在WrokSpace、stage和repo中的差別。

同樣diff可以支持分支之間的比較。

  • git diff branchName:把當前branch跟branchName進行比較,也可以使用”git diff branchNameA branchNameB”
  • git diff branchName — fileName:比較兩個branch的fileName文件差異

總結

通過這篇文章介紹了分支的基本使用,同時介紹了一個非常有用的stash命令。

在使用Git進行代碼控制中,分支是很容易創建的,所以也建議使用分支來進行開發新功能、bug修復。

 本文由用戶 jopen 自行上傳分享,僅供網友學習交流。所有權歸原作者,若您的權利被侵害,請聯系管理員。
 轉載本站原創文章,請注明出處,并保留原始鏈接、圖片水印。
 本站是一個以用戶分享為主的開源技術平臺,歡迎各類分享!