一个提交,是整个项目里所有文件的快照。git reset
和git checkout
命令可以针对整个提交,也可以针对单个文件,如果要对单个文件操作,参数里指定文件路径。git revert
命令只能针提交,不能针对单个文件。
reset 提交
在提交级别,reset/重置的作用是重新设置分支顶端,即把分支顶端指针移动到其他提交节点。这可以用于从当前分支中删除提交。例如,下面的命令将hotfix
分支向后移动2个提交。
git checkout hotfix
git reset HEAD~2
hotfix
分支原来顶端的2个提交现在悬空了,是孤立提交,它们将在下一次Git执行垃圾收集时被删除。换句话说,这2个提交被丢弃了。过程如下图所示:
git reset
主要用在本地环境,除了操作本地仓库中的分支,通过传入不同参数,还可以操作工作目录和暂存区:
--soft
– 不更新暂存区和工作目录。--mixed
– 暂存区被更新以匹配指定的提交,但工作目录不受影响。这是默认选项。--hard
– 暂存区和工作目录都将更新,以匹配指定的提交。
可以将这些模式理解为git reset
命令的作用范围。更多详细信息可参考帮助get help reset
。
checkout 旧提交
git checkout
命令可以将旧提交中的代码签出,更新本地状态。当签出分支时,即是在分支之间切换。
git checkout hotfix
在git内部,上述命令所做的只是将HEAD指针移动到另一个分支,并更新工作目录来匹配。由于这可能会覆盖本地更改,因此在这之前,Git会强制你提交或储藏工作目录中的更改。
git checkout
可以签出任意提交。这与签出分支的操作完全相同: 它将HEAD指针移动到指定的提交。例如,下面的命令将签出头部往后第2个提交:
git checkout HEAD~2
这对于快速检查项目的旧版本非常有用。但是,如果现在添加新提交,将会丢失原来头部的2个提交。因此,这种情况下,在添加提交之前,应该始终创建一个新分支。
使用 revert 撤销公共提交
revert通过创建新的反向提交来撤消提交。这是撤销更改的一种安全方法,因为它没有更改提交历史。例如,下面的命令将计算出最后一次提交所包含的更改,创建一个新的反向提交,来撤消这些更改。
git checkout hotfix
git revert HEAD~2
这可以理解为:
与此形成对比的是git reset
,它会更改现有的提交历史记录。因此,git revert
适用于撤销公共分支上的更改,而git reset
适用于撤销私有分支上的更改。
也有程序员将git revert
看作撤消已提交更改的工具,而git reset HEAD
则用于撤消未提交的更改。
与git checkout
一样,git revert
也有可能覆盖工作目录中的文件,因此它会要求你提交或储藏本地更改。