【问题标题】:Undo or remove changes from a previous Git commit [duplicate]撤消或删除先前 Git 提交的更改 [重复]
【发布时间】:2016-01-11 08:02:32
【问题描述】:

假设我有一个提交列表: A > B > C > D > E ,我怎样才能从历史中删除 C 中所做的更改,以拥有 A > B > D > E

【问题讨论】:

  • 您需要明确是否要将 C 保留在您的历史记录中,或者您是否只想在当前版本的代码库中撤消其更改,而您不在乎如果 C 仍在您的历史记录中。这对你来说重要吗?
  • 在这种情况下,我不关心 C 提交,我放弃它。

标签: git git-revert git-rewrite-history


【解决方案1】:

您可以随时恢复更改。

git revert C

如果你想重写历史,这就是rebase 的用途。您需要:

git rebase -i A

然后从提交列表中删除 C。

更长的解释:

第一个选项通过创建与原始提交相反的新提交来恢复更改。所以存储库看起来像:

A > B > C > D > E > C`

其中C`与C相反。基本上与patch --reverse相同

第二个选项改变历史。 rebase 允许您选择特定的提交、更改提交的顺序等等。我建议阅读git-rebase-i 标志用于交互模式,允许用户在变基之前编辑提交列表。

如果您从提交列表中删除 C 并执行变基,实际输出将是

A > B > D > E

分支中不再有 C 的历史记录。

注意:在这两种情况下,您都可能在流程中遇到冲突。 在第一种情况下,因为您将 C` 应用于 E,而在第二种情况下,因为您将 D 应用于 B。

【讨论】:

  • Tx Igal,你能详细说明一下你的答案吗?
  • 完成。编辑了我的答案。
  • 您应该提到,如果其他人的历史记录中也有提交 C,则不应使用 rebase。或者,如果这些人也可以在重写的提交之上重新设置/重做他们的工作,那么重新设置是可以的,但无论如何你都不能轻易地重新设置共享的历史记录。
【解决方案2】:

试试git revert C

...最好也阅读man git-revert

【讨论】:

    【解决方案3】:

    你做不到 并且获取A > B > D > E。 你最终会得到A > B > D' > E'

    要删除 C 中引入的更改,您可以使用

    git rebase --onto <newbase> <oldbase> <commit/branch>
    

    在你的情况下:

    git rebase --onto B C E
    

    这会将D..E 中引入的更改从旧的基础C 放到新的基础B(如果您没有遇到任何冲突),从而导致

    A > B > D' > E'
    

    重要要注意 DE 获取新的 sha ID 会导致 D'E' 所以如果您已经发布了 CD 或 @ 987654335@ 使用还原方法 (git revert C) 否则您可能会弄乱其他人的历史记录。

    【讨论】:

    • 所以这个答案有点误导。虽然确实 D 和 E 被重写以具有新的 sha ID,但每次提交引入的 更改 仍然相同。
    • 嗨..谢谢,我试图改写我的回答,以反映仍然可以删除在 C 中所做的更改,但不会以 E 的相同 sha ID 结束
    猜你喜欢
    • 2016-12-16
    • 2019-07-31
    • 1970-01-01
    • 2021-05-30
    • 2015-01-30
    • 2010-12-19
    • 2012-12-14
    • 2021-09-30
    • 2016-12-24
    相关资源
    最近更新 更多