Git 使用:git revert 与 git reset 的差异
引言
在使用 Git 进行版本控制时,git revert 和 git reset 是两个可能会用到的命令,但是现对于极其频繁的 push,pull,merge 指令来说,这两个命令的使用频率就非常低了,所以我就专门建了一个项目来做测试,各种提交 commit,然后各种 revert,reset,merge,以此来学习这两个命令,建议读者也这样做,纸上得来终觉浅,绝知此事要躬行,此处仅仅抛砖引玉。
git revert
命令概述
git revert用于撤销某个提交的更改,并生成一个新的提交来记录这个撤销操作。这个命令感觉非常好用,因为他很安全,主要的做法就是把原先的提交反向操作,然后生成一个新的提交,这样就保留了历史记录,同时又撤销了更改。所以这个 revert 是可以重复执行的,只是增加一些提交记录罢了,本身的代码都可以回溯,对应到 gitTortoise 中,就是按钮 revert change by this commit 这按钮,记住,这个的意思是 revert 你点击的这个按钮
实验下来是这样的,如果有 6 个提交,点击最开始的第一个提交,选择 revert 的话,会 revert 所有内容到当前分支的,包含当前分支的,就是说连带前六个提交一起 revert 掉了, revert 主要针对的是已经提交的内容,可以随意 revert,影响都不大

使用场景
- 当你需要保留项目的历史记录时,使用
git revert是一个安全的选择。 - 适用于公共分支,避免影响其他开发者的工作。
示例
1 | git revert <commit_hash> |
- 解释:此命令会创建一个新的提交,撤销指定提交的更改。
git reset
命令概述
git reset用于将当前分支的 HEAD 指针移动到指定的提交,并可以选择性地更改索引和工作目录。git reset更多的是将指针移动到指定的分支,同时会把原先的提交内容放到暂存区。- 如果是调试的话,这会比较方便。例如,使用
reset移动到某个指针,然后checkout掉这些提交内容进行调试。如果没有问题,可以通过git pull来还原到当前分支。 - 另一种情况是需要修改代码并推送到远程,此时必须使用
--hard-with-lease来安全地推送。切记,使用一般的push会报错,提示你需要pull。但一旦执行pull,就等于没修改了,必须使用force来强制覆盖远程。这种操作的复杂程度说明了其危险性,基本使用 IDE 进行操作。 - 即便是执行了
reset,也可以通过reFlog日志找到相关的提交,重新恢复代码。但是,如果本地的更改没有提交,就真的会丢失了。
- 如果是调试的话,这会比较方便。例如,使用
使用场景
- 当你需要彻底删除某个提交的更改时,使用
git reset是合适的选择。 - 适用于本地分支,尤其是在尚未推送到远程仓库的情况下。
示例
1 | git reset --hard <commit_hash> |
总结
在日常使用中,主要涉及的命令有 git commit、git push、git pull 和 git revert。
使用
git revert来撤销某个提交的更改,并保留历史记录。这非常适合处理线上问题。如果线上某个功能出现了问题,现场修复 Bug 是很困难的,最好的办法是执行revert,然后提交补丁代码。如果前后端分离,前端可以封闭入口并给出提示,后台则直接执行revert,重新部署,这样可以最大限度地减少影响。总的来说,只要是提交过的 commit,都可以重新恢复,恢复的难易程度取决于提交的复杂性。如果提交较复杂,可能需要多个
cherry-pick来恢复;如果提交简单,直接使用revert就可以恢复。cherry-pick的使用频率很高。当分支增多时,如果一个分支修复了一些 Bug,或者有一些临时功能需要合并到主线,就需要使用cherry-pick,以便逐步合并,最大程度地减少代码之间的干扰。对于单一功能点的合并,可以直接在主分支(即
main)上执行merge功能分支,解决冲突后再推送到远程。
参考资料
- Git 官方文档
- 版本控制相关书籍
- 在线 Git 教程


