天天看點

為什麼網際網路巨頭們紛紛使用Git而放棄SVN?(内含Git核心指令與原理總結)

Git與SVN的差別

存儲方式不同

Git把内容按中繼資料方式存儲類似k/v資料庫,而SVN是按檔案(新版SVN已改成中繼資料存儲)

這裡,我們給出一個簡單的Git使用示例。

cd .git/objects/df/
git cat-file -p df70460b4b4aece5915caf5c68d12f560a9de56e
echo 'version1' > text.txt
git hash-object -w text.txt      

使用方式不同

從本地把檔案推送遠端服務,SVN隻需要commint 而Git需要 add、commint、push 三個步驟。

比如,我們使用下圖來模拟SVN的使用過程。

為什麼網際網路巨頭們紛紛使用Git而放棄SVN?(内含Git核心指令與原理總結)

我們可以使用下圖來模拟Git的使用過程。

為什麼網際網路巨頭們紛紛使用Git而放棄SVN?(内含Git核心指令與原理總結)

版本的管理模式不同

Git是一個分布式的版本管理系統,而要SVN是一個遠端集中式的管理系統。

例如,我們可以使用下圖來表示SVN的集中式管理。

為什麼網際網路巨頭們紛紛使用Git而放棄SVN?(内含Git核心指令與原理總結)

我們可以使用下圖來表示Git的分布式管理。

Git核心命
為什麼網際網路巨頭們紛紛使用Git而放棄SVN?(内含Git核心指令與原理總結)
令總結

Git用戶端安裝

官方用戶端下載下傳:

https://git-scm.com/downloads

其他用戶端下載下傳:

https://tortoisegit.org/download/

Git指令的使用

(1)基于遠端倉庫克隆至本地

git clone <remote_url>      

(2)目前目錄初始化為git 本地倉庫

git init  <directory>      

(3)基于mvn 模闆建立項目

mvn archetype:generate      

本地添加

(1)添加指定檔案至暫存區

git add <fileName>      

(2)添加指定目錄至暫存區

git add <directory>      

(3)添加所有

git add -A      

(4)将指定目錄及子目錄移除出暫存區

git rm --cached target -r      

(5)添加忽略配置檔案 .gitignore

本地送出

(1)送出至本地倉庫

git commit file -m '送出的注釋資訊'      

(2)快捷送出至本地倉庫

git commit -am '快捷添加與送出'      

分支管理

(1)檢視目前分支

git branch [-avv]      

(2)基于目前分支建立分支

git branch <branch name>      

(3)基于送出建立分支

git branch <branch name> <commit id>
$ git branch -d {dev}      

(4)切換分支

git checkout <branch name>      

(5)合并分支

git merge <merge target>      

(6)解決沖突

如果因沖突導緻自動合并失敗,此時 status 為mergeing 狀态。需要手動修改後重新送出(commit)

遠端倉庫管理

(1)檢視遠端配置

git remote [-v]      

(2)添加遠端位址

git remote add origin http:xxx.xxx      

(3)删除遠端位址

git remote remove origin      

(4)上傳新分支至遠端

git push --set-upstream origin master      

(5)将本地分支與遠端建立關聯

git branch --track --set-upstream-to=origin/test test      

Tag管理

(1)檢視目前

git tag      

(2)建立分支

git tag <tag name> <branch name>      

(3)删除分支

git tag -d <tag name>      

日志管理

(1)檢視目前分支下所有送出日志

git log      

(2)檢視目前分支下所有送出日志

git log {branch}      

(3)單行顯示日志

git log --oneline      

(4)比較兩個版本的差別

git log master..experiment      

(5)以圖表的方式顯示送出合并網絡

git log --pretty=format:'%h %s' --graph      

Git底層原理

GIT存儲對像(hashMap)

Git 是一個内容尋址檔案系統,其核心部分是一個簡單的鍵值對資料庫(key-value data store),你可以向資料庫中插入任意内容,它會傳回一個用于取回該值的hash 鍵。

(1) Git 鍵值庫中插入資料

echo 'binghe' | git hash-object -w --stdin 79362d07cf264f8078b489a47132afbc73f87b9a      

(2)基于鍵擷取指定内容

git cat-file -p 79362d07cf264f8078b489a47132afbc73f87b9a      

Git基于該功能 把每個檔案的版本中内容都儲存在資料庫中,當要進行版本復原的時候就通過其中一個鍵将其取回并替換。

Git版本寫入與復原過程

(1)查找所有的git 對像

find .git/objects/ -type f      

(2)寫入版本1

echo 'version1' > README.MF; git hash-object -w README.MF;      

(3)寫入版本2

echo 'version2' > README.MF; git hash-object -w README.MF;      

(4)寫入版本3

echo 'version3' > README.MF; git hash-object -w README.MF;      

(5)復原指定版本

git cat-file -p c11e96db44f7f3bc4c608aa7d7cd9ba4ab25066e > README.MF      

是以我們平常用的 git add 其實就是把修改之後的内容 插入到鍵值庫中。當我們執行 git add README.MF 等同于執行了 git hash-object -w README.MF 把檔案寫到資料庫中。

我們解決了存儲的問題,但其隻能存儲内容同并沒有存儲檔案名,如果要進行復原 怎麼知道哪個内容對應哪個檔案呢?接下要我們就看下樹對象,它解決了檔案名存儲的問題 。

Git樹對象

樹對像解決了檔案名的問題,它的目的将多個檔案名組織在一起,其内包含多個檔案名稱與其對應的Key和其它樹對像的用引用,可以了解成作業系統當中的檔案夾,一個檔案夾包含多個檔案和多個其它檔案夾。

每一個分支當中都關聯了一個樹對像,他存儲了目前分支下所有的檔案名及對應的 key。通過以下指令即可檢視

git cat-file -p master^{tree}      

Git送出對象

一次送出即為目前版本的一個快照,該快照就是通過送出對像儲存,其存儲的内容為:一個頂級樹對象、上一次送出的對像啥希、送出者使用者名及郵箱、送出時間戳、送出評論。

$ git cat-file -p b2395925b5f1c12bf8cb9602f05fc8d580311836 
tree 002adb8152f7cd49f400a0480ef2d4c09b060c07 
parent 8be903f5e1046b851117a21cdc3c80bdcaf97570 
author binghe <[email protected]> 1532959457 +0800 
committer binghe <[email protected]> 1532959457 +0800      

綜上,我們可以推測出從修改一個檔案到送出的過程總共生成了三個對象:

  • 一個内容對象:存儲了檔案内容
  • 一個樹對像:存儲了檔案名及内容對像的key
  • 一個送出對像:存儲了樹對像的key 及送出評論。

Git引用

當我們執行 git branch {branchName} 時建立了一個分支,其本質就是在git 基于指定送出建立了一個引用檔案,儲存在 .git\refs\heads\ 下。

(1)建立分支

git branch dev 
 cat.git\refs\heads\dev      

Git總共 有三種類型的引用:

  • 分支引用
  • 遠端分支引用
  • 标簽引用

(2)查詢比較兩個版本

git log master..experiment      

(3)版本送出曆史網絡

git log --pretty=format:'%h %s' --graph      

(4)檢視分支樹

git cat-file -p master^{tree}