Chapter 08
撤销与回退
掌握 git reset 三种模式、git revert 安全撤销以及 reflog 紧急救援,从容应对各种"后悔"场景。
reset 三种模式
git reset --soft 是什么效果? 只移动 HEAD 指针,暂存区和工作区保持不变。所有被"回退"的 commit 的修改仍然保留在暂存区中,随时可以重新提交。
适用场景:commit 信息写错了、想把多个 commit 合并成一个、重新整理提交历史。
适用场景:commit 信息写错了、想把多个 commit 合并成一个、重新整理提交历史。
git reset --mixed(默认)是什么效果? 移动 HEAD 指针 + 重置暂存区(index),但工作区的文件修改保持不变。被回退的修改从暂存区退回到工作区,变为"未暂存"状态。
适用场景:提交后发现漏了一些文件、想重新选择要暂存的内容。
适用场景:提交后发现漏了一些文件、想重新选择要暂存的内容。
git reset 不加参数等同于 git reset --mixed。 git reset --hard 是什么效果? 移动 HEAD 指针 + 重置暂存区 + 丢弃工作区所有修改。这是最彻底的回退,所有未提交的修改都会被永久删除。
适用场景:确定要完全丢弃所有修改、回到某个确定的历史状态。
适用场景:确定要完全丢弃所有修改、回到某个确定的历史状态。
⚠️ --hard 危险警告
git reset --hard 会永久丢失未提交的修改!一旦执行,工作区和暂存区的所有更改都无法通过 Git 恢复(除非你有其他备份或使用 reflog 找回 commit)。请务必在确认不再需要这些修改后再使用。对于已 push 到远程的 commit,绝对不要使用 reset,应改用 git revert。 欢迎使用 git reset 练习终端!跟随步骤操作,体验三种 reset 模式的区别。
$
revert 与 reflog
git revert 和 git reset 有什么区别?revert:创建一个新的 commit 来"反向"撤销指定 commit 的修改。不改写历史,安全且适合协作场景。
reset:直接回退分支指针,会改写提交历史。
核心原则:已 push 的提交用 revert,未 push 的用 reset。改写已 push 的历史会导致协作者的仓库混乱。
reset:直接回退分支指针,会改写提交历史。
核心原则:已 push 的提交用 revert,未 push 的用 reset。改写已 push 的历史会导致协作者的仓库混乱。
已经 push 的提交怎么安全撤销?
使用
如果要撤销连续的多个 commit:
git revert <hash>,Git 会生成一个反向 commit,抵消目标 commit 的所有修改。原始 commit 仍保留在历史中,非常安全。如果要撤销连续的多个 commit:
git revert HEAD~3..HEADgit reflog 是什么? reflog 记录了 HEAD 的每一次移动——包括 commit、reset、checkout、merge 等所有操作。即使你执行了
默认保留 90 天(可通过
reset --hard,reflog 中仍然保留着之前的 commit hash。默认保留 90 天(可通过
gc.reflogExpire 配置)。reflog 是 Git 中的"后悔药",是 reset --hard 之后最后的恢复手段。 误操作
reset --hard 后怎么恢复?git reflog # 找到误操作之前的 commit hash git reset --hard <hash> # 跳回那个 commitreflog 中每条记录都有索引(如
HEAD@{2}),也可以直接用索引:git reset --hard HEAD@{2}只想应用某个提交的部分修改怎么办?
使用
git add -p 进行交互式暂存。Git 会逐块(hunk)展示差异,你可以选择 y(应用)、n(跳过)、s(进一步拆分)等,精确控制要暂存的内容。 💡 安全操作习惯
在执行任何 reset 操作前,先用 git stash 备份当前修改,或者用 git branch backup 创建一个备份分支。这样即使操作失误,也能轻松找回。 模拟场景:你刚刚执行了 git reset --hard HEAD~1,丢失了重要提交。
别慌!用 reflog 来恢复。
$
