28

如果我将更改存储在一个分支中然后删除该分支会发生什么?

(1) 我会丢失隐藏的更改吗?

例子:

git stash
git checkout other_branch
git branch -D previous_branch

(2) 此外,上述存储和删除步骤是否等同于在分支中提交更改然后删除该分支(就达到的最终状态而言)?IE:

git commit -m "Dummy commit, I am terminating this branch"
git checkout other_branch
git branch -D previous_branch
4

2 回答 2

20

(1) 否。保存的更改git stash被保存为一对(或有时三个)提交。这些提交由名称引用stash。如果您将分支名称和标签视为提交的标签(它们就是这样,那么您可以绘制图片,例如:

          O1 - O2             <-- other_branch
        /
M1 - M2 - M3 - M4             <-- master
   \
     B1 - B2 - B3             <-- branch
      .
       .......................<-- tag

(如果我可以对标签进行不同的着色,这可能会更好;我用点表示标签tag指向 commit B1,即“在分支上branch”)。

如果您在分支上branch并且有一些未保存的更改并运行git stash,这就是它的作用:

        /
M1 - M2 - M3 - M4             <-- master
   \
     B1 - B2 - B3             <-- HEAD=branch
                | \
                i - w ........<-- stash

(我离开了图表other_branchtag但他们仍然在那里。我写信HEAD=branch暗示那HEAD指向branch,并且branch指向 commit B3。)

这里是您编辑的“索引”和“工作树”i状态。该名称直接指向 commit ,并且有两个父级(即,即使它根本不是真正的合并,也是一个“合并提交”),作为它的第一个父级和第二个父级。wstashstashwwB3i

当您运行时git branch -D,您所做的就是擦除标签。所以假设你git checkout other_branch,然后擦除标签branch。现在你有了这个:

          O1 - O2             <-- HEAD=other_branch
        /
M1 - M2 - M3 - M4             <-- master
   \
     B1 - B2 - B3
                | \
                i - w ........<-- stash

没有直接的标签,B3但 stash 指向w,又w指向B3。所以一切都还在那里,只要 stash(或 reflog,或两者兼而有之)保持B3在 git 的内部雷达上,它就会一直存在。

(2) 否:如您所见,stash 仍然有对分支的引用。然而,一旦你放下那个存储——例如,擦除stash标签git stash drop——你会得到这个:

          O1 - O2             <-- HEAD=other_branch
        /
M1 - M2 - M3 - M4             <-- master
   \
     B1 - B2 - B3
                | \
                i - w

如果您git add-ed 和git commited 所有更改,您将获得(单个,非合并)提交,我们可以将其称为B4, on branch。分支标签将被移动到指向B4,然后您将签出other_branch并删除标签,给出:

          O1 - O2             <-- HEAD=other_branch
        /
M1 - M2 - M3 - M4             <-- master
   \
     B1 - B2 - B3 - B4

这几乎(但不完全)相同。

(请注意,如果 tagtag仍然指向B1,则 commitB1将一直存在,直到标签也被删除。通过 或 through 提交B2B4只要B2它们w保持在那里,但在 reflog 中不可见,就会一直存在。30 天后(或其他任何时间)您为 reflog expiry 设置),reflog 条目过期,并且这些提交变得有资格进行垃圾收集。)

于 2013-09-18T08:59:37.237 回答
7
  1. 存储获取工作目录的脏状态并将其保存在堆栈中。如果你存储一些东西然后删除之前的分支,你存储的更改不会消失。您可以使用以下命令列出存储堆栈上的内容:

git 存储列表

事实上,您可以保存一个存储,切换到另一个分支,然后尝试重新应用存储。不需要在同一个分支上应用存储。

在第二种情况下,您仍然需要在应用 stash 后执行 git commit。

于 2013-09-18T09:00:28.677 回答