撤销与清理

这一类命令有些只移动暂存区,有些会删除本地改动。执行前先确认自己要撤销的是“暂存状态”还是“文件内容本身”。

git restore <file>

git restore -- README.md

用途:把指定工作区路径恢复为暂存区(index)里的内容。只有 index 与 HEAD 相同时,结果才等同于恢复到 HEAD。

若明确要忽略 index 并从当前提交恢复:

git restore --source=HEAD -- README.md

旧写法:

git checkout -- README.md

会丢失本地内容

如果这个文件里有未保存到提交或 stash 的修改,执行后这些修改会被覆盖。

建议先看:

git diff -- README.md

git restore --staged --worktree <file>

git restore --staged --worktree -- README.md

用途:同时撤销指定文件的暂存内容和工作区内容,让文件回到当前 HEAD 版本。

旧写法:

git checkout HEAD -- README.md

适用场景:

  • 某个文件已经暂存,但后来确认完全不需要这些修改。

注意:这比只运行 git reset -- README.md 更强,因为它会改工作区文件内容。

git revert:保留历史地撤销提交

git revert --no-edit HEAD

用途:根据目标提交生成一个反向变化,并创建新提交。它不删除原提交,适合已共享历史中的普通提交。

使用前:

  • 先用 git show HEAD 确认目标;练习时只撤销专门创建的普通测试提交。
  • 工作区应干净;若反向变化冲突,需要人工解决后继续,或用 git revert --abort 中止。
  • merge commit 需要额外选择主线父提交,初学者不要随意对 merge commit 运行 revert。
  • --no-edit 沿用自动生成的消息,避免练习时被未知编辑器阻塞;真实项目仍应按团队要求审查消息。

git reset --hard

git reset --hard

用途:把当前分支、暂存区和工作区一起重置到 HEAD,丢弃所有已跟踪文件的本地修改。

高风险操作

这个命令会删除已跟踪文件的未提交修改;为写回目标提交,它还可能删除阻碍已跟踪路径写入的未跟踪文件或目录。reflog 不能找回从未提交的工作区内容。只在可丢弃的隔离仓库中使用,并先运行 git status --short、git diff 与 git diff --staged。

常见安全替代:

git stash
git status --short

如果只是想取消暂存,不要用 --hard,用:

git reset

git clean

git clean

用途:删除未被 Git 跟踪的文件。实际使用中通常需要加 -f,因为 Git 默认会保护性拒绝直接删除。

建议流程:

git clean -n -d
git clean -fd

说明:

  • -n 是 dry run,只显示将删除什么,不真正删除。
  • -f 表示确认执行。
  • -d 表示包含未跟踪目录。
  • 默认不删除被 ignore 的路径;-x 才会把 ignored 路径纳入,初学主线不练这个选项。
  • 嵌套 Git 仓库还有额外保护,不要通过叠加 -f 去绕过不理解的边界。

不会进入提交历史

未跟踪文件没有被 Git 保存。删除后通常不能通过 Git 恢复。

git stash

git stash

用途:临时保存当前已跟踪文件的暂存与未暂存修改,并清理这些修改。若仍有未跟踪或 ignored 路径,工作区不一定完全干净。

适用场景:

  • 需要临时切换分支,但当前工作还不适合提交。
  • 想先把本地修改挪开,拉取远程更新或复现问题。

常用补充命令:

git stash list
git stash pop
git stash apply

说明:

  • pop 会应用最近一次 stash,并在成功后删除该 stash。
  • apply 只应用,不删除 stash 记录。
  • 默认 git stash 不包含未跟踪或 ignored 文件;-u 包含未跟踪文件,-a 才连 ignored 文件一起包含。执行前先检查清单,避免把凭据带进 stash。

选择撤销命令的判断表

目标影响历史是否适合共享历史推荐命令
只取消暂存,保留文件内容不变是git restore --staged -- README.md
用 index 内容覆盖工作区文件不变是,但会丢本地内容git restore -- README.md
用 HEAD 同时覆盖 index 与工作区不变是,但会丢本地内容git restore --source=HEAD --staged --worktree -- README.md
反向撤销一个已共享普通提交新增反向提交通常是git revert --no-edit HEAD
移动本地分支并保留文件修改改写当前分支入口尚未共享时才考虑git reset --mixed HEAD~1
丢弃全部已跟踪本地修改分支目标可变,文件会丢否,仅隔离仓库git reset --hard HEAD
删除未跟踪文件不进入历史且通常不可恢复与历史无关,但高风险先 git clean -n -d,隔离仓库才考虑 git clean -fd
临时挪开已跟踪修改历史不变,新增 stash 引用本地操作git stash push -m "wip: explain purpose"

最小练习

在 版本控制实战与自测 的隔离仓库中,分别验证“恢复工作区”“取消暂存”和“revert 专用普通提交”。每一步都记录前后的 status、diff、diff --staged 和 log,并写明内容、index、历史与分支指针各自是否变化。

参考资料

按 Git 2.55.0 官方文档核验,获取日期:2026-07-14。