3

我有一个分支,我在几个提交中对几个文件进行了一些更改。有一次,不久前,我开始对这些文件的一个子集做一些工作,并检查了一些更改。在那之后,我们决定将这些文件作为在另一个分支中完成的事情的一部分删除。因此,我想“取消”这些文件 - 它们与我在分支中所做的事情不再相关,并且我不想因此与其他已删除的文件造成任何合并冲突。

有什么方法可以更新进行这些更改的提交以使这些文件保持不变,并且在我的分支历史记录之外

更具体地说:

在当前状态下考虑以下源代码树:

src/A.java
src/B.java
src/C.java
src/D.java

在历史记录中大约有 10 次左右的提交,进行了一次提交,以下列方式进行了更改:

M   src/B.java
M   src/C.java
A   src/D.java

有没有办法可以C.java从历史记录中删除更改,这样当您查看上面的提交时,它看起来像

M   src/B.java
A   src/D.java

如您所见,它会出现,以至于C.java我的分支从未接触过。

我已经看过了git revert,但是在不创建新提交的情况下无法找到一种方法来做到这一点,这会重置旧提交所做的更改。我知道我也可以通过简单地删除我的分支中的文件来避免合并冲突,但这感觉就像一个“丑陋”的解决方案,这一次有效,但下一次可能不行(如果另一个分支中的更改不是删除,怎么办?但是修改?),所以如果有更清洁的方法我想学习它。

4

1 回答 1

1

尽管RyPeck RyPeck现在删除的答案与评论中使用的一种很好的方法相关联git filter-branch,但我以不同的方式解决了它,所以我想我会分享我是如何做到的 - 如果没有其他目的,那么作为未来的参考我(谁将不可避免地不得不再次在互联网上问这个问题,可能很快......):

首先,我使用git rebase -i master. 这打开了我的文本编辑器(我碰巧将 git 配置为打开 Notepad++),文件类似于:

pick First commit message
pick Second commit message
pick This is where I touched the files I didn't want to touch
pick Another commit
pick This goes on for a while
pick I think you get the point
pick I'll stop now

接下来是一些关于如何编辑文件的评论。我所做的是用我想要更改的提交更改行

...
edit This is where I touched the files I didn't want to touch
...

然后保存并关闭编辑器。然后发生的是 git 应用了三个第一个提交,然后停止并说

Stopped at <hash>... This is where I touched the files I didn't want to touch
You can amend the commit now, with

    git commit --amend

Once you are satisfied with your changes, run

    git rebase --continue

然后,我将文件重置为提交之前的状态,使用类似于

git reset HEAD^ src/C.java # undoes the changes to the file
git add src/C.java         # stages the undoing of the changes
git commit --amend         # amends the undoing to the last commit

之后,提交更改了文件两次——首先是我所做的更改,然后再次返回——并且 git 将这两组更改压缩为一组,在其中它们取消并且什么都不做。我现在跑

git rebase --continue

完成工作。如果我现在看一下 的历史src/C.java,就会发现这组提交一无所获。

这种技术非常灵活——使用edit提交模式,您可以对它进行任何更改。

于 2013-07-08T22:43:49.917 回答