??現(xiàn)在是凌晨?jī)牲c(diǎn)沮协,你正在趕一份工作報(bào)告谦铃,你在readme.txt中添加了一行:
$ cat readme.txt
Git is a distributed version control system.
Git is free software distributed under the GPL.
Git has a mutable index called stage.
Git tracks changes of files.
My stupid boss still prefers SVN.
??在你準(zhǔn)備提交前,你猛然發(fā)現(xiàn)了“stupid boss”可能會(huì)讓你丟掉這個(gè)月的獎(jiǎng)金赞厕!既然錯(cuò)誤發(fā)現(xiàn)得很及時(shí)艳狐,就可以很容易地糾正它。你可以刪掉最后一行皿桑,手動(dòng)把文件恢復(fù)到上一個(gè)版本的狀態(tài)毫目。如果用git status查看一下:
$ git status
# On branch master
# Changes not staged for commit:
# (use "git add..." to update what will be committed)
# (use "git checkout --..." to discard changes in working directory)
#
# modified: readme.txt
#
no changes added to commit (use "git add" and/or "git commit -a")
你可以發(fā)現(xiàn)蔬啡,Git會(huì)告訴你,git checkout -- file可以丟棄工作區(qū)的修改:
$ git checkout -- readme.txt
??命令git checkout -- readme.txt意思就是镀虐,把readme.txt文件在工作區(qū)的修改全部撤銷箱蟆,這里有兩種情況:
一種是readme.txt自修改后還沒(méi)有被放到暫存區(qū),現(xiàn)在刮便,撤銷修改就回到和版本庫(kù)一模一樣的狀態(tài)空猜;
一種是readme.txt已經(jīng)添加到暫存區(qū)后,又作了修改恨旱,現(xiàn)在辈毯,撤銷修改就回到添加到暫存區(qū)后的狀態(tài)。
??總之搜贤,就是讓這個(gè)文件回到最近一次git commit或git add時(shí)的狀態(tài)∽晃郑現(xiàn)在,看看readme.txt的文件內(nèi)容:
$ cat readme.txt
Git is a distributed version control system.
Git is free software distributed under the GPL.
Git has a mutable index called stage.
Git tracks changes.
文件內(nèi)容果然復(fù)原了仪芒。
??git checkout -- file命令中的--很重要管毙,沒(méi)有--,就變成了“切換到另一個(gè)分支”的命令桌硫,我們?cè)诤竺娴姆种Ч芾碇袝?huì)再次遇到git checkout命令。
??現(xiàn)在假定是凌晨3點(diǎn)啃炸,你不但寫(xiě)了一些胡話铆隘,還git add到暫存區(qū)了:
$ cat readme.txt
Gitis a distributed version control system.
Gitis free software distributed under theGPL.
Githas a mutable index called stage.
Gittracks changes of files.
Mystupid boss still prefersSVN.
$ git add readme.txt
??慶幸的是,在commit之前南用,你發(fā)現(xiàn)了這個(gè)問(wèn)題膀钠。用git status查看一下,修改只是添加到了暫存區(qū)裹虫,還沒(méi)有提交:
$ git status
# On branch master
# Changes to be committed:
# (use "git reset HEAD..." to unstage)
#
# modified: readme.txt
#
??Git同樣告訴我們肿嘲,用命令git reset HEAD file可以把暫存區(qū)的修改撤銷掉(unstage),重新放回工作區(qū):
$ git reset HEAD readme.txt
Unstaged changes after reset:
M readme.txt
??git reset命令既可以回退版本筑公,也可以把暫存區(qū)的修改回退到工作區(qū)雳窟。當(dāng)我們用HEAD時(shí),表示最新的版本匣屡。
再用git status查看一下封救,現(xiàn)在暫存區(qū)是干凈的,工作區(qū)有修改:
$ git status
# On branch master
# Changes not staged for commit:
# (use "git add..." to update what will be committed)
# (use "git checkout --..." to discard changes in working directory)
#
# modified: readme.txt
#
no changes added to commit (use "git add" and/or "git commit -a")
還記得如何丟棄工作區(qū)的修改嗎捣作?
$ git checkout -- readme.txt
$ git status
# On branch master
nothing to commit (working directory clean)
??現(xiàn)在誉结,假設(shè)你不但改錯(cuò)了東西,還從暫存區(qū)提交到了版本庫(kù)券躁,怎么辦呢惩坑?還記得版本回退一節(jié)嗎掉盅?可以回退到上一個(gè)版本。不過(guò)以舒,這是有條件的趾痘,就是你還沒(méi)有把自己的本地版本庫(kù)推送到遠(yuǎn)程。還記得Git是分布式版本控制系統(tǒng)嗎稀轨?我們后面會(huì)講到遠(yuǎn)程版本庫(kù)扼脐,一旦你把“stupid boss”提交推送到遠(yuǎn)程版本庫(kù),你就真的慘了……
小結(jié)
場(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操作雌澄。
場(chǎng)景3:已經(jīng)提交了不合適的修改到版本庫(kù)時(shí)斋泄,想要撤銷本次提交,參考版本回退一節(jié)镐牺,不過(guò)前提是沒(méi)有推送到遠(yuǎn)程庫(kù)炫掐。