13

假设我有 8 次提交和一个分支(主)的线性 git 历史记录:

1 -> 2 -> 3 -> 4 -> 5 -> 6 -> 7 -> [8=master]

我想将 master 移到 4 (我可以用git branch -f master 4):

1 -> 2 -> 3 -> [4=master] -> 5 -> 6 -> 7 -> 8

现在工作树处于状态 4。

我现在想将更改应用4 -> 8到我的工作树作为补丁。

也就是说,在不影响 .git 文件夹的状态的情况下,我想将未暂存的更改应用4->8到我的工作树。在此之后,工作树应该处于状态 8,但提交状态和主分支应该处于状态 4。

另一种说法:假装在将 master 移动到 4 之后,我手动将 4->8 更改到我的工作树,而没有将它们添加到索引中。结果应该是一样的。

最简单的方法是什么?

4

5 回答 5

16

我知道我迟到了,但对于其他人来说,我认为最简单的方法是:

git cherry-pick --no-commit 4..8

于 2014-10-28T21:34:25.463 回答
5
git format-patch 4..8 | xargs git apply

[编辑:下面评论中的下一个跳过制作单个补丁文件]

git diff 4..8 | git apply
于 2013-01-09T22:58:10.027 回答
2

在您的情况下,如果您实际上并不关心“未分级”位,那么最简单的事情可能就是

git checkout 8 -- .

这将更新您的树和索引以匹配提交 8,而不会更改您的提交历史。然后您可以git reset放弃索引更改。

如果您确实希望保持索引文件不受干扰,则稍微复杂一些,因为 git 总是从索引更新工作树。你可以做类似的事情

GIT_INDEX_FILE=/tmp/foo git checkout 8 -- .

这将使用该路径/tmp/foo作为此命令的临时索引文件。之后您可能想删除此文件。


在更复杂的情况下,您想要重新应用实际上不会让您回到提交 8 的精确状态的补丁,您可以使用git cherry-pick --no-commit commit1 commit2 ...按顺序应用提交。当然,这仍然会修改索引。

于 2013-01-09T22:47:42.903 回答
0
 git checkout master@{1} -- .

是你所需要的全部。它读取“签出 master 前一次指向的提交的文件”。结帐git reflog以查看其工作原理。

此外,您不应该像以前那样强行重新创建分支。这将允许 git 跟踪 master 曾经指向的所有地方。利用

git stash -u 

如果您在工作目录中有一些工作。然后

git reset --hard master^^^^

或者

git reset --hard master~4
于 2013-01-10T00:08:36.867 回答
0
git cherry-pick master~4 master~5 master~6 master~7 master~8

你的工作树必须是干净的

git help cherry-pick
于 2014-09-05T15:27:18.767 回答