提问人:hasen 提问时间:3/28/2009 最后编辑:Peter Mortensenhasen 更新时间:7/1/2023 访问量:922982
撤消 Git 中一个文件的工作副本修改
Undo working copy modifications of one file in Git
问:
在最后一次提交后,我修改了工作副本中的一堆文件,但我想撤消对其中一个文件的更改,就像将其重置为与最近提交相同的状态一样。
但是,我只想撤消仅一个文件的工作副本更改,没有其他任何内容。
我该怎么做?
答:
如果您只想撤消上一次提交对该文件的更改,您可以尝试以下操作:
git checkout branchname^ filename
这将检出上次提交前的文件。如果您想再进行几次提交,请使用表示法。branchname~n
评论
branchname^
只需使用
git checkout filename
这会将 filename 替换为当前分支中的最新版本。
警告:您的更改将被丢弃 - 不保留备份。
评论
git checkout x
--
--
--
你可以使用
git checkout -- file
您可以在没有 (如 nimrodm 建议的那样)的情况下执行此操作,但如果文件名看起来像分支或标记(或其他修订标识符),它可能会混淆,因此最好使用。--
--
您还可以检出文件的特定版本:
git checkout v1.2.3 -- file # tag v1.2.3
git checkout stable -- file # stable branch
git checkout origin/master -- file # upstream master
git checkout HEAD -- file # the version from the most recent commit
git checkout HEAD^ -- file # the version before the most recent commit
评论
git reset HEAD <filename> ; git checkout -- <filename>
git help rev-parse
。HEAD^^
HEAD^^^
HEAD~2
HEAD~3
HEAD^2
HEAD^
HEAD~
git checkout <commit> <filename>
我今天使用它是因为我意识到当我升级到 drupal 6.10 时,我的网站图标在几次提交前被覆盖了,所以我必须把它拿回来。这是我所做的:
git checkout 088ecd favicon.ico
评论
git log --oneline <filename>
将为您提供更紧凑的日志,并且仅包含对特定文件的更改
git reflog <filename>
我使用 SHA id 恢复我的文件,我所做的是git checkout <sha hash id> <file name>
如果您的文件已经暂存(在编辑文件后执行 git add 等操作时发生)以取消暂存更改。
用
git reset HEAD <file>
然后
git checkout <file>
如果尚未暂存,只需使用
git checkout <file>
评论
如果您尚未推送或以其他方式共享您的提交:
git diff --stat HEAD^...HEAD | \
fgrep filename_snippet_to_revert | cut -d' ' -f2 | xargs git checkout HEAD^ --
git commit -a --amend
我总是对此感到困惑,所以这里有一个提醒测试用例;假设我们有这个脚本来测试:bash
git
set -x
rm -rf test
mkdir test
cd test
git init
git config user.name test
git config user.email [email protected]
echo 1 > a.txt
echo 1 > b.txt
git add *
git commit -m "initial commit"
echo 2 >> b.txt
git add b.txt
git commit -m "second commit"
echo 3 >> b.txt
此时,更改不会暂存到缓存中,因此:git status
$ git status
On branch master
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)
modified: b.txt
no changes added to commit (use "git add" and/or "git commit -a")
如果从这一点开始,我们这样做,结果是这样的:git checkout
$ git checkout HEAD -- b.txt
$ git status
On branch master
nothing to commit, working directory clean
相反,如果我们这样做,结果是:git reset
$ git reset HEAD -- b.txt
Unstaged changes after reset:
M b.txt
$ git status
On branch master
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)
modified: b.txt
no changes added to commit (use "git add" and/or "git commit -a")
因此,在这种情况下 - 如果更改未暂存,则没有区别,同时覆盖更改。git reset
git checkout
现在,假设上面脚本的最后一个更改是暂存/缓存的,也就是说,我们在最后也做了。git add b.txt
在本例中,此时为:git status
$ git status
On branch master
Changes to be committed:
(use "git reset HEAD <file>..." to unstage)
modified: b.txt
如果从这一点开始,我们这样做,结果是这样的:git checkout
$ git checkout HEAD -- b.txt
$ git status
On branch master
nothing to commit, working directory clean
相反,如果我们这样做,结果是:git reset
$ git reset HEAD -- b.txt
Unstaged changes after reset:
M b.txt
$ git status
On branch master
Changes not staged for commit:
(use "git add <file>..." to update what will be committed)
(use "git checkout -- <file>..." to discard changes in working directory)
modified: b.txt
no changes added to commit (use "git add" and/or "git commit -a")
因此,在这种情况下 - 如果更改是暂存的,基本上会将暂存更改为未暂存的更改 - 而将完全覆盖更改。git reset
git checkout
此答案适用于撤消相同或多个文件夹(或目录)中的多个特定文件中的本地更改所需的命令。 此答案专门解决了用户有多个文件但用户不想撤消所有本地更改的问题:
如果您有一个或多个文件,则可以将相同的命令 ( ) 应用于 每个文件都列出它们的每个位置,以 空间如下:
git checkout -- file
git checkout -- name1/name2/fileOne.ext nameA/subFolder/fileTwo.ext
注意上面 name1/name2/fileOne.ext nameA/subFolder/fileTwo.ext 之间的空格
对于同一文件夹中的多个文件:
如果您碰巧需要放弃对 特定目录,请使用 git checkout,如下所示:
git checkout -- name1/name2/*
上面的星号可以撤消 name1/name2 下该位置的所有文件。
同样,以下内容可以撤消所有文件中的更改 多个文件夹:
git checkout -- name1/name2/* nameA/subFolder/*
再次注意 name1/name2/* nameA/subFolder/* 之间的空格 以上。
注意:name1、name2、nameA、subFolder - 所有这些示例文件夹名称都表示相关文件可能驻留的文件夹或包。
如果已提交,您可以还原文件的更改并再次提交,然后使用上次提交压缩新提交。
评论
对我来说,只有这个有效
git checkout -p filename
我已经通过 git bash 完成了:
(use "git checkout -- <file>..." to discard changes in working directory)
- Git 状态。[因此,我们看到一个文件被修改了。
- git checkout -- index.html [我在索引中更改了.html文件:
- git status [现在删除了这些更改]
git checkout a3156ae4913a0226caa62d8627e0e9589b33d04c -p */SearchMaster.jsp
故障: a3156ae4913a0226caa62d8627e0e9589b33d04c = 这是提交的哈希值。它在我自己的个人分支(不是主人)上。
-p 标志是路径。
*/SearchMaster,.jsp 是文件名。
Git 2.23 引入了一个来做到这一点,我认为,这是为了让这些问题的答案变得简单明了。restore
git restore [--] <pathspec>...
与往常一样,可能需要 ,但当文件名以破折号开头时。(这里不可能与分支名称混淆,因为 的边界不包括分支,这与 do-all 不同--
restore
checkout
)
为了完成,还可以使用 恢复暂存文件,并从与 不同的提交中恢复。restore
--staged
HEAD
--source=<tree>
评论
git restore .
git checkout
是这样做的旧方法。2020 年更新后,首选方式是:
git restore file.txt
请参阅此重复答案(请务必向下滚动到 2020 年更新):https://stackoverflow.com/a/31281748/12763497
上一个:如何复制文件
下一个:为什么文本文件应该以换行符结尾?
评论