【學了就忘】Git操作 — 61.rebase命令詳解

在 Git 中合併來自不同分支的修改主要有兩種方法:mergerebase

在之前的文章當中我們介紹了git merge命令的用法,通過git merge命令我們可以對兩個分支進行合併操作。這樣我們可以很方便地進行協同開發了,每個人都在自己的分支下開發代碼,開發完畢之後再合併到master分支,通過這種方式可以保證大家的代碼不會陷入混亂。

但是這樣也會有隱含的缺陷:

  • 一個是提交歷史記錄的不完整,回退的時候可選擇性減少。
  • 一個是歷史提交記錄非常的混亂,會讓你眼花繚亂,欲仙欲死。

爲了解決這些頭疼的問題,我們就需要用到git rebase操作。

1、git rebase命令簡介

rebase有兩個意思:變基衍合,即變換分支參考的基準點。默認情況下,一個分支會以該分支上的第一次提交作爲基點。

如下圖所示:master分支默認以提交1st作爲基點:


如果以提交4th作爲master分支的基點,master分支就會變爲:

這個變化基準點的過程就稱之爲變基(rebase)。

接下來詳細介紹一下rebase命令

官方對於rebase的描述爲:“git-rebase: Forward-port local commits to the updated upstream head”— git doc

翻譯一下,就是將你在某個分支上的所有提交記錄,移花接木到另一個分支上。

這邊需要強調一個概念:reapply,使用rebase並不是簡單地像你進行剪切複製一樣,rebase命令會依次地,將你所要操作分支上的所有提交,應用到目標分支上。

也就是說,實際上在執行rebase命令的時候,有兩個隱含的注意點:

  1. 在重放之前提交的時候,Git會創建新的提交。也就是說即使你重放的提交與之前的一模一樣,Git也會將他當做新的獨立的提交進行處理。
  2. git rebase命令並不會刪除舊的提交。也就是說,你在對某個分支執行了rebase操作之後,老的提交仍然會存放在.git文件夾的objects目錄下。

2、merge與rebase的區別

git rebase 命令與git merge 命令的功能十分相似,不過二者的工作方式有着顯著的差異。

比如:將AB兩分支進行合併:

  • A分支上執行git merge B,表示的是將B分支合併到A分支上;
  • 而在A分支上執行git rebase B,則表示將A分支通過變基合併到B分支上;(看不懂,往下看)

(1)採用merge合併分支

現在有兩個分支master分支和dev分支,如果想要將dev分支合併到master分支上。根據三方合併原則,需要在c4c6和它們的公共父提交節點c2的基礎上進行合併。

如下圖:

合併後生成一個新的提交c7,該提交有兩個父節點c4c6

具體的合併方式爲:如果沒有衝突git就會自動採用Fast-forward方式進行合併,如果有衝突就進行典型合併,解決衝突後再進行手動合併。

如下圖:

(2)採用rebase合併分支

我們希望dev分支變基合併到master分支上,所以首先切換到dev分支(注意這裏與採用merge方法時所在的分支相反):

如下圖:


執行命令:

# 切換分支
$ git checkout dev

# 再進行rebase合併
$ git rebase master

合併後的結果,如下圖:

注意

被合併的master分支保持不動,而合併它的dev分支,將自己的提交作爲補丁(patch)一個個應用(applying)到master指向的分支上。

在這個過程中Git會自動創建c5'c6'提交。原來的c5c6提交就沒用了,會被git gc回收(就是不顯示在歷史記錄中了,但是數據還在,應該用git reflog命令可以看到)。

合併後分支Git版本庫中的提交記錄變成了一條直線,如下圖:

(3)總結rebase命令

基於以上表述,我們可以得出git rebase命令的工作流程:

  • 在對特定分支進行rebase操作之後,其等效於創建了新的提交。
  • 並且老的提交也沒有被銷燬,只是簡單地不能再被訪問或者使用。
  • 之前分支的章節我們曾經提及,分支只是一個執行提交的指針。因此如果沒有分支或者Tag指向某個提交,該提交將無法再被訪問使用,但是該提交會一直存在於你的文件系統中,佔用着你的磁盤存儲。

git rebase master命令的意思

該指令翻譯過來就是:重新定位當前工作的分支,以master 分支做爲新的基準點,即使用 master 分支所指向的提交,作爲我新的基準點。

  • git merge 要合併的分支 命令:切換的主要的分支,把其他的分支合併過來。
  • git rebase 變基的目標分支 命令:切換到被合併的分支上,把該分支上的提交變基到目標分支上。

參考:

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章