【Tools】git操作总结
git操作總結(jié)
下載的工程帶有子工程submodule:
當(dāng)使用git clone下來(lái)的工程中帶有submodule時(shí),初始的時(shí)候,submodule的內(nèi)容并不會(huì)自動(dòng)下載下來(lái)的,此時(shí),只需執(zhí)行如下命令:
git submodule update --init --recursive即可將子模塊內(nèi)容下載下來(lái)。
常用的撤銷操作
(1)撤銷本地工作區(qū)修改:
git checkout -- <file> 撤銷某個(gè)file文件修改 或 git checkout . 撤銷全部文件的修改,但是不能把新增的文件刪除。該命令是用版本庫(kù)里的版本替換 工作區(qū)的版本,替換為上一次add的版本,就相當(dāng)于撤銷,無(wú)論工作區(qū)是修改還是刪除,都可以“一鍵還原”。(2)撤銷已經(jīng)add到暫存區(qū)的修改
git reset HEAD <file> 或 git reset HEAD .(3)撤銷已經(jīng)commit到版本庫(kù)中的修改
可參考 https://www.jianshu.com/p/c2ec5f06cf1a
git reset --soft HEAD^ # 把當(dāng)前版本回退到上一個(gè)版本,會(huì)保留工作區(qū)修改,和暫存區(qū)修改,即只撤銷commit操作,add后的內(nèi)容和工作區(qū)的內(nèi)容都不會(huì)撤銷。 或 git reset (--mixed,該參數(shù)可省略) HEAD^ # 把當(dāng)前版本回退到上一個(gè)版本,會(huì)保留工作區(qū)修改,即變?yōu)榱薬dd之前的狀態(tài)。 或 git reset commit_id # 把當(dāng)前版本回退到commit_id版本號(hào),會(huì)保留工作區(qū)修改,變?yōu)榱薬dd之前的狀態(tài) 或 git reset --hard commit_id # 把當(dāng)前版本回退到某個(gè)版本號(hào),會(huì)把工作區(qū)的所有文件都變回為 commit_id 版本,不會(huì)保留工作區(qū)修改 或 git reset --hard HEAD^ # 把當(dāng)前版本回退到上一個(gè)版本,不會(huì)保留工作區(qū)修改。解決沖突的操作步驟
解決沖突之后需要add和commit一遍,還是只需要commit一遍?應(yīng)該是add+commit吧
先add,再commit,然后才能 git pull --rebase origin 遠(yuǎn)程分支名,不add,或者不commit,就不可能pull成功。
git pull --rebase origin 遠(yuǎn)程分支名后會(huì)有沖突,解決沖突之后使用 git rebase --continue
然后再 git commit --amend --no-edit這樣就不用重新編輯commit信息,(此時(shí)不需要再執(zhí)行g(shù)it pull --rebase origin 遠(yuǎn)程分支名了),然后再 git push origin 本地分支:遠(yuǎn)程分支
git diff
git diff commit_id file_name 查看file_name文件和commit_id提交的不同 git diff branch_name file_name 查看file_name文件在本分支和branch_name分支的不同覆蓋已經(jīng)push到遠(yuǎn)程倉(cāng)庫(kù)分支的提交內(nèi)容 --force-with-lease
當(dāng)我們push到遠(yuǎn)程分支后,發(fā)現(xiàn)有問(wèn)題想修改卻又想去掉遠(yuǎn)程倉(cāng)庫(kù)的本次提交,并且此時(shí)沒有別人向遠(yuǎn)程分支push過(guò)內(nèi)容,就可以使用下面的命令
git reset commit_id # 這個(gè)id是上一次的(別人)提交的id,撤銷已commit的修改 git add file # 把修改的文件再重新add一遍 git commit -m "mesage" # 這里的commit消息可以與我們想要覆蓋的消息不一樣,執(zhí)行下面的最后一步后覆蓋掉之前的提交的的 git push origin branch_name --force-with-lease # 直接git push origin branch_name會(huì)被rejected,加上--force-with-lease就可以成功推送然后覆蓋遠(yuǎn)程的提交而不產(chǎn)生一個(gè)新提交。禁止使用git push --force來(lái)推送,因?yàn)檫@樣強(qiáng)制推送會(huì)覆蓋掉別人遠(yuǎn)程的提交,造成
只提交一部分修改文件,另一部分修改文件不提交
將需要提交的修改文件 git add file_1 file_2,然后git commit -m "message",剩下的不想提交的都git stash``,然后git pull --rebase,然后git push,最后再git stash pop```就可以彈出之前沒有提交的文件,并且這些文件中我們修改過(guò)的部分還在。
配置
git config --global user.name "Your Name" git config --global user.email "email@example.com"注意git config命令的--global參數(shù),用了這個(gè)參數(shù),表示你這臺(tái)機(jī)器上所有的Git倉(cāng)庫(kù)都會(huì)使用這個(gè)配置,當(dāng)然也可以對(duì)某個(gè)倉(cāng)庫(kù)指定不同的用戶名和Email地址。
git diff可以查看修改內(nèi)容
git diff readme.txt
版本回退
版本回退主要兩個(gè)命令:
git reset --hard HEAD^ # 把當(dāng)前版本回退到上一個(gè)版本和
git reset --hard commit_id # 把當(dāng)前版本回退到某個(gè)版本號(hào)詳細(xì)解釋如下:
在Git中,用HEAD表示當(dāng)前版本,也就是最新的提交1094adb...,上一個(gè)版本就是HEAD^,上上一個(gè)版本就是HEAD^^,當(dāng)然往上100個(gè)版本寫100個(gè)^比較容易數(shù)不過(guò)來(lái),所以寫成HEAD~100。
現(xiàn)在,我們要把當(dāng)前版本回退到上一個(gè)版本,就可以使用git reset命令:
git reset --hard HEAD^HEAD指向的版本就是當(dāng)前版本,HEAD^指向的版本就是上一個(gè)版本.
Git允許我們?cè)诎姹镜臍v史之間穿梭,使用命令:
git reset --hard commit_idcommit id(版本號(hào))是一大串類似1094adb…
穿梭前,用git log可以查看提交歷史,以便確定要回退到哪個(gè)版本。
要重返未來(lái),用git reflog查看命令歷史,以便確定要回到未來(lái)的哪個(gè)版本。
工作區(qū)、暫存區(qū)、版本庫(kù)
工作區(qū)就是本地修改的文件,在電腦里能看到的目錄,比如我的study-cidi文件夾就是一個(gè)工作區(qū);
第一步是用git add把文件添加進(jìn)去,實(shí)際上就是把文件修改添加到暫存區(qū);
第二步是用git commit提交更改,實(shí)際上就是把暫存區(qū)的所有內(nèi)容提交到當(dāng)前分支;
版本庫(kù)包含暫存區(qū)stage和master分支和Head指針,Git的版本庫(kù)里存了很多東西,其中最重要的就是稱為stage(或者叫index)的暫存區(qū),還有Git為我們自動(dòng)創(chuàng)建的第一個(gè)分支master,以及指向master的一個(gè)指針叫HEAD。
撤銷修改
(1)命令git checkout -- readme.txt意思就是,把readme.txt文件在工作區(qū)的修改全部撤銷。命令中的兩個(gè)橫杠--很重要,沒有--,就變成了“切換到另一個(gè)分支”的命令。git checkout -- readme.txt其實(shí)是用版本庫(kù)里的版本替換工作區(qū)的版本,替換為上一次add的版本,就相當(dāng)于撤銷,無(wú)論工作區(qū)是修改還是刪除,都可以“一鍵還原”。
(2)命令git reset HEAD <file>可以把暫存區(qū)的修改撤銷掉(unstage),重新放回工作區(qū),如:
git reset HEAD readme.txt可把已經(jīng)add到暫存區(qū)的文件修改撤銷掉。
場(chǎng)景1:當(dāng)你改亂了工作區(qū)某個(gè)文件的內(nèi)容,想直接丟棄工作區(qū)的修改時(shí):
用命令git checkout -- file
場(chǎng)景2:當(dāng)你不但改亂了工作區(qū)某個(gè)文件的內(nèi)容,還添加到了暫存區(qū)時(shí),想丟棄修改:
分兩步,第一步用命令git reset HEAD <file>,就回到了場(chǎng)景1,第二步按場(chǎng)景1操作:
git reset HEAD <file> # 把已經(jīng)```add```到暫存區(qū)的文件修改撤銷掉,這一步后只剩下工作區(qū)的修改了 git checkout -- file # 把file文件在工作區(qū)的修改全部撤銷。場(chǎng)景3:已經(jīng)提交了不合適的修改到版本庫(kù)時(shí),想要撤銷本次提交,參考版本回退一節(jié),不過(guò)前提是沒有推送到遠(yuǎn)程庫(kù):
版本回退主要兩個(gè)命令:
git reset --hard HEAD^ # 把當(dāng)前版本回退到上一個(gè)版本和
git reset --hard commit_id # 把當(dāng)前版本回退到某個(gè)版本號(hào)(1)撤銷本地工作區(qū)修改:
git checkout -- <file> 撤銷某個(gè)file文件 或 git checkout . 撤銷全部文件的修改,但是不能把新增的文件刪除。該命令是用版本庫(kù)里的版本替換工作區(qū)的版本,替換為上一次add的版本,就相當(dāng)于撤銷,無(wú)論工作區(qū)是修改還是刪除,都可以“一鍵還原”。(2)撤銷已經(jīng)add到暫存區(qū)的修改
git reset HEAD <file> 或 git reset HEAD .(3)撤銷已經(jīng)commit到版本庫(kù)中的修改
git reset --hard HEAD^ # 把當(dāng)前版本回退到上一個(gè)版本 或 git reset --hard commit_id # 把當(dāng)前版本回退到某個(gè)版本號(hào)刪除文件
??當(dāng)你把文件git add test.txt添加到版本庫(kù)后,想要?jiǎng)h除該文件,可以 rm test.txt,也可以手動(dòng)刪除,然后Git知道你刪除了文件,因此,工作區(qū)和版本庫(kù)就不一致了,接下來(lái)就需要在版本庫(kù)中刪除test.txt,使用git rm test.txt,注意這兩個(gè)命令加不加git是有差別的。要從版本庫(kù)中刪除該文件,那就用命令git rm test.txt刪掉,并且git commit -m 'msg'.
當(dāng)你rm刪錯(cuò)某個(gè)文件了(不是git rm),因?yàn)榘姹編?kù)里還有呢,所以可以很輕松地把誤刪的文件恢復(fù)到最新版本:
git checkout -- test.txtgit checkout -- test.txt其實(shí)是用版本庫(kù)里的版本替換工作區(qū)的版本,無(wú)論工作區(qū)是修改還是刪除,都可以“一鍵還原”。
注意:從來(lái)沒有被添加到版本庫(kù)就被刪除的文件,是無(wú)法恢復(fù)的!
SSH
????為什么GitHub需要SSH Key呢?因?yàn)镚itHub需要識(shí)別出你推送的提交確實(shí)是你推送的,而不是別人冒充的,而Git支持SSH協(xié)議,所以,GitHub只要知道了你的公鑰,就可以確認(rèn)只有你自己才能推送。
??Git支持多種協(xié)議,包括https,但通過(guò)ssh支持的原生git協(xié)議速度最快。使用https除了速度慢以外,還有個(gè)最大的麻煩是每次推送都必須輸入口令,但是在某些只開放http端口的公司內(nèi)部就無(wú)法使用ssh協(xié)議而只能用https。
????第1步:創(chuàng)建SSH Key。在用戶主目錄下,看看有沒有.ssh目錄,如果有,再看看這個(gè)目錄下有沒有id_rsa和id_rsa.pub這兩個(gè)文件,如果已經(jīng)有了,可直接跳到下一步。如果沒有,打開Shell(Windows下打開Git Bash),創(chuàng)建SSH Key:
ssh-keygen -t rsa -C "youremail@example.com"你需要把郵件地址換成你自己的郵件地址,然后一路回車,使用默認(rèn)值即可,由于這個(gè)Key也不是用于軍事目的,所以也無(wú)需設(shè)置密碼。
如果一切順利的話,可以在用戶主目錄里找到.ssh目錄,里面有id_rsa和id_rsa.pub兩個(gè)文件,這兩個(gè)就是SSH Key的秘鑰對(duì),id_rsa是私鑰,不能泄露出去,id_rsa.pub是公鑰,可以放心地告訴任何人。
??第2步:登陸GitHub,打開“Account settings”,“SSH Keys”頁(yè)面,然后,點(diǎn)“Add SSH Key”,填上任意Title,在Key文本框里粘貼id_rsa.pub文件的內(nèi)容.點(diǎn)“Add Key”,你就應(yīng)該看到已經(jīng)添加的Key.
關(guān)聯(lián)遠(yuǎn)程庫(kù)
要關(guān)聯(lián)一個(gè)遠(yuǎn)程庫(kù),使用命令
git remote add origin git@server-name:path/repo-name.git關(guān)聯(lián)后,使用命令git push -u origin master第一次推送master分支的所有內(nèi)容;
此后,每次本地提交后,只要有必要,就可以使用命令git push origin master推送最新修改;
分支
Git鼓勵(lì)大量使用分支:
1.查看分支:git branch
2.創(chuàng)建分支:git branch <name>
3.切換分支:git checkout <name>
注意區(qū)分git checkout -- readme.txt是撤銷工作區(qū)修改的指令,不要混淆了
4.創(chuàng)建+切換分支:git checkout -b <name>
相當(dāng)于執(zhí)行下面這兩條命令:
git branch <name> git checkout <name>5.合并某分支到當(dāng)前分支:git merge <name>
6.刪除分支:git branch -d <name>
7.查看分支合并圖:git log --graph
每個(gè)歷史一行:git log --graph --pretty=oneline
每個(gè)歷史一行,并且commit_id使用縮略:git log --graph --pretty=oneline --abbrev-commit
8.查看命令歷史:git reflog
合并分支 和 Fast forward
需要把某個(gè)分支branch-1合并到另一個(gè)分支branch-2,需要先切換到branch-2:git checkout branch-2,然后再合并git merge branch-1即可。
git checkout master git merge dev上面這種合并分支時(shí),由于當(dāng)前 master 分支所在的提交對(duì)象是要并入的 dev 分支的直接上游,Git 只需把 master 分支指針直接右移。換句話說(shuō),如果順著一個(gè)分支走下去可以到達(dá)另一個(gè)分支的話,那么 Git 在合并兩者時(shí),只會(huì)簡(jiǎn)單地把指針右移,因?yàn)檫@種單線的歷史分支不存在任何需要解決的分歧,所以這種合并過(guò)程可以稱為快進(jìn)(Fast forward)。
??合并分支時(shí),加上--no-ff參數(shù)就可以用普通模式合并,合并后的歷史有分支,能看出來(lái)曾經(jīng)做過(guò)合并,而fast forward合并就看不出來(lái)曾經(jīng)做過(guò)合并。
準(zhǔn)備合并dev分支,請(qǐng)注意–no-ff參數(shù),表示禁用Fast forward:
git merge --no-ff -m "merge with no-ff" dev因?yàn)楸敬魏喜⒁獎(jiǎng)?chuàng)建一個(gè)新的commit,所以加上-m參數(shù),把commit描述寫進(jìn)去。
master分支應(yīng)該是非常穩(wěn)定的,也就是僅用來(lái)發(fā)布新版本,平時(shí)不能在上面干活;
干活都在dev分支上,也就是說(shuō),dev分支是不穩(wěn)定的,到某個(gè)時(shí)候,比如1.0版本發(fā)布時(shí),再把dev分支合并到master上,在master分支發(fā)布1.0版本;
你和你的小伙伴們每個(gè)人都在dev分支上干活,每個(gè)人都有自己的分支(例如:我的是zhuhz分支),時(shí)不時(shí)地把(zhz分支)往dev分支上合并即可,不要合并到master。
bug分支
之所以用到git stash暫存工作現(xiàn)場(chǎng),而不提交,并不是你不想提交,而是工作只進(jìn)行到一半,還沒法提交,預(yù)計(jì)完成還需1天時(shí)間。但是,必須在兩個(gè)小時(shí)內(nèi)修復(fù)該bug,怎么辦?
幸好,Git還提供了一個(gè)stash功能,可以把當(dāng)前工作現(xiàn)場(chǎng)“儲(chǔ)藏”起來(lái),等以后恢復(fù)現(xiàn)場(chǎng)后繼續(xù)工作.
疑問(wèn):為什么不add一下,并不commit,這樣不行嗎?還是說(shuō)add之后就會(huì)把所有的各個(gè)分支上add的東西都放在了一起,你下次在add別的分支上的修改之后add了commit,也會(huì)把我現(xiàn)在這個(gè)分支上的修改給一起commit?記得試驗(yàn)一下。弄懂原因。
git stash git stash listGit把stash內(nèi)容存在某個(gè)地方了,但是需要恢復(fù)一下,有兩個(gè)辦法:
一是用git stash apply恢復(fù),但是恢復(fù)后,stash內(nèi)容并不刪除,你需要用git stash drop來(lái)刪除;
另一種方式是用git stash pop,恢復(fù)的同時(shí)把stash內(nèi)容也刪了.
在master分支上修復(fù)的bug,想要合并到當(dāng)前dev分支,可以用git cherry-pick <commit_id>命令,把bug提交的修改“復(fù)制”到當(dāng)前分支,避免重復(fù)勞動(dòng)。
修改最近一次的commit內(nèi)容
git commit --amend然后會(huì)自動(dòng)在用默認(rèn)編輯器vim中打開一個(gè)文件COMMIT_EDITMSG,修改第一行信息即可。如果是默認(rèn)vim,那不會(huì)有問(wèn)題,如果是默認(rèn)是gedit,這種方法沒用,只能改為默認(rèn)用vim編輯,方法是git config --global core.editor vim。
git commit -am "haha"等價(jià)于下面兩條命令:
git add . git commit -m "haha"總結(jié)
以上是生活随笔為你收集整理的【Tools】git操作总结的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問(wèn)題。
- 上一篇: 虚函数和纯虚函数的区别
- 下一篇: 【深度学习】pytorch-tensor