簡體   English   中英

Git:將存儲庫更新為某個版本

[英]Git: update a repository to certain revision

假設我有一個版本號為A的存儲庫。我想將其更新到版本B,而最新版本是C.(版本A早於B,B早於C)。 我是git的新手,所以我做了一些研究,發現了這個 ,這激發了我一個解決方案:

git pull # update from A to the latest revision C
git reset --hard B

這確實有效。 但是因為我不能直接從A中git reset --hard B ,所以先前更新到最新仍然太重,我不知道可能有一些單行命令來滿足我的需要。 有什么提示嗎?

沒有“將存儲庫更新為某個版本”。 您的存儲庫具有所有版本,這就是git fetch / git pull所做的。

如果您想在本地工作樹中放置一個特定的repo版本,有幾種方法可以做到這一點。 最接近您的問題是:

更新本地存儲庫:

git fetch origin

創建一個新的分支(從你當前所在的任何分支,我們稍后將重置,所以它無關緊要):

git branch yourbranchname
git checkout yourbranchname

上述兩個操作可以縮寫為一個(當前HEAD被假定為分支的源):

git checkout -b yourbranchname

然后將該分支的指針放在您需要的提交中( B ):

git reset --hard sha1-of-B

git reset --hard將始終有效,它不依賴於你的分支的歷史,它工作的唯一條件是提交B在你的本地對象庫中(即B必須存在並且必須從遠程倉庫獲取這不是你的工作)。

正如@Hasturkun指出的那樣,你也可以使用額外的參數直接從任意哈希分支:

git checkout -b yourbranchname SHA-1

你需要使用git checkout 做就是了:

git checkout B

你會有那個修改。

你的方法是完全錯誤的。 您正在修改您不想修改的內容:您當前的分支(可能是master分支)。

一個簡單的線性git存儲庫就是這樣一個提交鏈

*---A---*---*---B---*---*---C
    ^                       ^
    |                       |
  master              origin/master
    ^
    |
   HEAD

這是您調用git fetch之后的存儲庫狀態。 請注意,包含所有中間步驟的整個歷史記錄就在您的本地硬盤驅動器上。 只是你只有一個狀態在提交A簽出( HEAD指向master指向A ),所以你看到的文件屬於那個狀態。

現在,如果您只想查看作為B提交的狀態,您可以使用git checkout B檢查該提交。 這會將您看到的文件更新為B狀態,並在該提交時指向HEAD

*---A---*---*---B---*---*---C
    ^           ^           ^
    |           |           |
  master       HEAD   origin/master

HEAD總是引用git認為你所在的提交/分支,並在你調用git status時將它與你的工作目錄進行比較。

如果您只想查看該提交,那么簡單的git checkout B就足夠了。 如果您確實想要進行已提交並希望保留的更改,則應引入新分支來記錄這些更改。 這是通過git checkout B之后的簡單git checkout -b newBranch實現的。 這將給你國家

*---A---*---*---B---*---*---C
    ^           ^           ^
    |           |           |
  master    newBranch origin/master
                ^
                |
               HEAD

這只是提供一個名稱來提交B而不是其哈希值。 經過多次提交后,您的狀態將如下所示:

*---A---*---*---B---*---*---C
    ^           |           ^
    |           |           |
  master         \    origin/master
                   \
                    *---*---D
                            ^
                            |
                        newBranch
                            ^
                            |
                           HEAD

關鍵是,在使用git checkout ...一些其他分支/提交后,您可以通過調用git checkout newBranch輕松返回提交D ,並且永久引用會從垃圾收集提交D停止git


現在,為什么使用git reset --hard壞? 首先,它會破壞您尚未提交的所有本地更改,恕不另行通知。 其次,如果你不小心,它可能會讓你失去歷史。

例如,考慮一下您在上次推送到上游存儲庫后進行了一些更改,並想查看一些歷史提交B (與你的問題中的情況有些相反。)歷史看起來像這樣:

  *---A---*---*---B---*---*---C
      ^                       ^
      |                       |
origin/master               master
                              ^
                              |
                             HEAD

使用git reset --hard B ,您將獲得以下狀態:

  *---A---*---*---B-(-*---*---C )
      ^           ^
      |           |
origin/master   master
                  ^
                  |
                 HEAD

括號中的提交不再由任何分支直接或間接引用,並且可能隨時被垃圾收集。 git可能不是非常積極的垃圾收集, 但如果它在你處於這種狀態時進行垃圾收集,你沒有辦法讓你恢復提交C ,它將永遠丟失 你不希望這種情況發生,所以養成使用git reset --hard的習慣並不是一個好主意。

如果您使用git checkout ,分支master仍然會指向C ,您仍然可以使用簡單的git checkout master返回它。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM