【學習筆記】Git的使用與版本控制

Git的使用與版本控制

所有的素材均來自於https://morvanzhou.github.io/tutorials/others/git/。本文只是個人學習的筆記記錄,如果想要學習,強烈建議去聽聽Morvan老師的課程,一聽就懂,一學就會。

基本配置與操作

創建版本庫 (init)

  1. 通過iTerm2 cd到版本庫所在的文件夾下
  2. 通過命令$ git init來建立新的git管理庫

添加文件管理 (add)

  • $ git status用於查看版本庫的狀況(包括文件所處的狀態:untracked/tracked/modified/unmodified…;
  • $ git add [filename]用於將文件加入版本庫,使之成爲staged狀態;
  • $ git add .可以將文件夾中所有未被添加的文件加入版本庫;

示意圖

提交改變 (commit)

$ git commit -m "comment"命令將staged狀態的文件commit成umodified狀態,利用comment來註釋本次修改的內容,以便後期查閱

修改記錄

log

  • $ git log可以查看詳細的修改記錄
  • $ git log --oneline可以查看修改記錄的簡要信息

status

  • $ git status用於查看版本庫的狀況(包括文件所處的狀態:untracked/tracked/modified/unmodified…
  • $ git status -s可以查看縮略版的版本庫狀況

diff

  • $ git diff用於查看還沒被add,也就是處於unstaged狀態的修改部分和上一個commit的文件的區別
  • $ git diff --cached用於查看已經被add,也就是處於staged狀態,但是未被commit的修改部分與上一個commit的文件的區別
  • $ git diff HEAD用於查看已經被add和未被add,但是均爲被commit的內容與上一個commit版本的區別
# 對比三種不同 diff 形式
$ git diff HEAD     # staged & unstaged

@@ -1 +1,3 @@
-a = 1  # 已 staged
+a = 2  # 已 staged
+b = 1  # 已 staged
+c = b  # 還沒 add 卻 stage (unstaged)
-----------------------
$ git diff          # unstaged

@@ -1,2 +1,3 @@
 a = 2  # 注: 前面沒有 +
 b = 1  # 注: 前面沒有 +
+c = b  # 還沒 add 去 stage (unstaged)
-----------------------
$ git diff --cached # staged

@@ -1 +1,2 @@
-a = 1  # 已 staged
+a = 2  # 已 staged
+b = 1  # 已 staged
​```

版本回退

amend

在上一個版本中添加一個新文件,可以使用$ git commit --amend --no-edit來操作,其中的“–no-eit"表示不編輯, 直接合併到上一個 commit

reset

當文件通過add操作後,處於staged狀態後,回到add之前的狀態,可以利用$ git reset [filename]來實現。其本質是利用reset,使狀態指針回到上一個commit的版本。

  • 對於以下情況的記錄,
$ git log --oneline
# 輸出
904e1ba change 2
c6762a1 change 1
13be9a7 create 1.py
​```

(1) 回到change2狀態

$ git reset --hard HEAD

(2) 回到change1狀態

  • $ git reset --hard HEAD^
  • $ git reset --hard c6762a1

(3) 回到更後面的狀態

  • $ git reset --hard HEAD~3表示回到前面第三個狀態,~3表示3個^
  • $ git reset --hard [id]用狀態id直接回到改狀態

如果回到過去後還想回到將來,可以首先通過$ git reflog來查看所有對HEAD指針做過的改動,並找到目標的commit id,例如下面這種情況,回到了change 1狀態後,想再回到change 2,可以發現change 2的狀態(在change 2做了amend的行爲,所以id=904e1ba)

$ git reflog
# 輸出
c6762a1 HEAD@{0}: reset: moving to c6762a1
904e1ba HEAD@{1}: commit (amend): change 2
0107760 HEAD@{2}: commit: change 2
c6762a1 HEAD@{3}: commit: change 1
13be9a7 HEAD@{4}: commit (initial): create 1.py

$ git reset --hard 904e1ba

checkout

利用$ git checkout [commit_id] -- [filename]來指定對某一個file,回到具體某一個commit id時的版本狀態。

分支管理

查看分支

通過$ git log --oneline --graph可以查看圖形化的master和branch情況

建立分支

分支的作用通常用於開發版本的建立和公開版本的維護。通過分支branch和master的搭配可以在不影響主版本的情況下進行新版本的開發和調試。

branch方法

通過$ git branch [branch name]的方式進行分支的添加

checkout方法

通過$ git checkout -b [branch name]的方式可以直接添加一個新的branch並將指針移到該branch中。此外,如果已經建立了新的branch可以通過$ git checkout [branch name]的方式切換分支

分支中操作

在分支中的修改

$ git commit -am "[comment]"的方式可以將修改的文件直接add並進行-mcomment操作。這種情況下,如果該文件事先不在repo中是無法操作的(需要amend操作將文件先加入版本庫中)

將分支的內容push到master中

  1. 首先要切換到master中,才能將branch的內容push過來,用$ git checkout master來進行切換
  2. 使用$ git mergh --no-ff -m "[comment]" [branch name]的操作方式,將其他版本的數據合併到當前的master版本中。其中,--no-ff的參數表示,不使用$ git merge默認的Fast forward格式進行merge的操作(因爲那樣不會保留commit信息),log中也不會保留graph。

分支衝突的解決

merge方法

merge

當修改同時發生在master(C3)和一個branch(C4)中時,要將master合併branch的內容會產生分支衝突的情況(C4和C3的前序文件信息不同),此時會在master的該文件中報錯:

a = 1
# I went back to change 1
<<<<<<< HEAD
# edited in master  	###在master中的信息
=======
# edited in dev			###在被合併的分支中中的信息
>>>>>>> dev

此時,需要將master中的該文件進行手動處理,並提交commit即可$ git commit -am "solve conflict",此時的log文件會顯示出衝突和合並的情況:

$ git log --oneline --graph

# 輸出
*   7810065 solve conflict			###衝突解決後的log信息(和commit id)
|\  
| * f7d2e3a change 3 in dev			###*在分支
* | 3d7796e change 4 in master		###*在master
|/  
* 47f167e back to change 1 and add comment for 1.py
* 904e1ba change 2
* c6762a1 change 1
* 13be9a7 create 1.py

rebase方法

假設共享的 branch 是 branch B,而我在 branch A 上工作, 有一天我發現branch B已經有一些小更新,我也想試試我的程序和這些小更新兼不兼容, 我也我想合併, 這時就可以用 rebase 來補充我的分支branch B的內容。補充完以後,和後面那張圖的 merge 不同,我還是繼續在 C3 上工作,不過此時的 C3 的本質卻不一樣了,因爲吸收了那些小更新。所以我們用 C3' 來代替。



可以看出 rebase 改變了 C3 的屬性,C3 已經不是從 C1 衍生而來的了。這一點和 merge 不一樣。merge在合併的時候創建了一個新的 C5 commit。這一點不同,使得在共享分支中使用 rebase 變得危險。如果是共享分支的歷史被改寫。別人之前共享內容的 commit 就被你的 rebase 修改掉了。

### 在自己的分支上(C3)使用rebase。
$ git rebase [branch name]

### 這時候一定會出現報錯並給予提示:
#When you have resolved this problem, run "git rebase --continue".
#If you prefer to skip this patch, run "git rebase --skip" instead.
#To check out the original branch and stop rebasing, run "git rebase --abort".

###當在自己的branch完成修改後可以選擇以上三種方式,繼續rebase(git rebase --continue)/跳過本次rebase(git rebase --skip)/直接放棄rebase(git rebase --abort)

臨時修改

Stash方法

當在分支上做代碼調試和修改時,突然來了新的需求,這時候需要對手頭的工作進行臨時儲存(不選擇進行直接commit是爲了保持每一次commit的內容都是有價值的,否則之後的log會非常難看)。這時候就可以選擇使用$ git stash對代碼進行臨時的儲存,然後切換其他分支進行操作完後,回到本分支使用$ git stach pop調出之前暫存的內容,就可以繼續愉快的coding啦。

在線管理GitHub

對於本地已經git init了的git管理庫,使用

$ git remote add origin https://github.com/xxx/xxx.git
$ git push -u origin master     # 推送本地 master 去 origin
$ git push -u origin dev        # 推送本地 dev  去 origin

就可以上傳到在線的github管理庫中了。


over

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