git rev-parse HEAD
显示当前的提交(将分支“重置”为)。但是,无论“重置”提交如何如何获取上一次的将来提交?
编辑:
git log --all -1 --pretty=format:"%H"
似乎有效,但是对于这个简单的任务,我真的必须使用其他命令吗?
Edit2:不,这不起作用。它显示03317b1d158cd8a79ff4083884eaf3a2eee3b136,这是最后一个和当前...之间的提交。
上下文:
在TortoiseGit中,我选择一些旧版本,然后选择Reset "master" to this
这= 051741bc532257903f3563d7d89c69cfdddaaf17
最新提交= 19747382e3680bd90689e998834b492aa66c0730
执行完此操作后,git rev-parse HEAD
显示051741bc532257903f3563d7d89c69cfdddaaf17
如何显示19747382e3680bd90689e998834b492aa66c0730?
答案 0 :(得分:1)
我认为您在这里误解。特别是,您不希望首先使用git reset
。这样做后,您可能需要再次使用它来解决问题。
请注意,git rev-parse master
将名称master
转换为提交哈希ID。通过遵循the gitrevisions documentation中概述的六步过程来做到这一点。这发现master
是refs/heads/master
的缩写,并且refs/heads/master
标识了一个特定的提交,因此,在完成所有工作之后,git rev-parse
产生的是提交哈希ID。>
特殊名称HEAD
始终是当前提交。但是它可以通过以下两种方式之一成为当前提交:
特殊名称包含分支的(全)名称,例如cat .git/HEAD
产生ref: refs/heads/master
。然后,名称refs/heads/master
实际上拥有当前提交的ID,git rev-parse HEAD
首先读取.git/HEAD
来发现这一事实,然后将refs/heads/master
转换为哈希ID。>
该提交是当前的提交。
或者,特殊名称HEAD
包含原始提交哈希ID。也就是说,cat .git/HEAD
会产生很大的丑陋哈希ID。您处于Git所说的分离头模式,git rev-parse HEAD
产生相同的哈希ID。
该提交是当前的提交。
请注意,这意味着您可以通过两种方式向Git询问HEAD
。一种方法是询问: HEAD
保留什么分支名称?仅当HEAD
没有分离时,此问题才有答案。第二种方法是问: HEAD
意味着什么提交哈希ID?这个问题几乎总是有答案的。 1
在任何情况下,每个提交都存储其直接前任或 parent 提交(或具有多个直接前任的提交)的哈希ID。大多数提交只有一个父母。因此,有了提交哈希ID,您可以轻松地向后。但是您不能继续,因为提交一旦完成,就会永久冻结。在该提交中 之后进行的任何提交的ID在该提交中均不可用。
这意味着,通常来说,为最新提交保留名称 。使用该名称,我们可以一次回退一次,一次提交更早。如果要使用该提交,则可以使用分离式HEAD模式。而且,如果我们处于分离式HEAD模式,则可以返回名称以找到 latest 提交,然后一次后退一个提交,直到达到分离式HEAD提交。无论我们在之前上执行什么提交,我们都会退回到该提交,这就是给定名称方向上的下一个提交。
我认为图片更清晰:
I <-J <-- br1
/
... <-F <-G <-H <-- HEAD
\
K <-L <-- br2
在这里,我们处于分离的HEAD模式,其中HEAD
包含一些哈希ID H
。因此,当前的提交本身就是H
。但是有两个可能的 next 提交。从br1
开始,我们将提交J
,它表示返回到I
,后者表示返回到H
。或者,从br2
开始,我们在L
处,它要返回到K
,后者要返回到H
。因此,在H
之后的下一个向前提交是 K
或 L
,并且不可能说出哪个,除非您选择终点。
要选择终点,最好将br1
和br2
单独放置,以便它们分别继续指向J
和L
。如果我们将标签br1
剥离J
并使其指向H
,我们将不再知道如何找到I
和J
。 / p>
......在TortoiseGit中,我选择一些旧版本,然后选择
Reset "master" to this
您最初没有(在您的标签中也没有提及)TortoiseGit,但我从未使用过它,但是this web page表示此重置调用了git reset
。
git reset
的作用-好,它可以做的许多事情之一,以及在特定情况下的作用-是更改存储在分支名称中的哈希ID 。因此,如果全名为master
的分支名称refs/heads/master
之前包含19747382e3680bd90689e998834b492aa66c0730
,但是随后Git用051741bc532257903f3563d7d89c69cfdddaaf17
覆盖了它,那么您将不再具有{{1} },其中包含数字master
。如果没有 other 名称包含该数字,那么唯一记住该数字的唯一方法就是将其写下来。
使用命令行Git,然后您可以运行19747382e3680bd90689e998834b492aa66c0730
将该数字写回到git reset master 19747382e3680bd90689e998834b492aa66c0730
,因为已将其写下来。这行得通,但通常不是一个好的计划-您应该一直在使用分离的HEAD模式或至少从分离的HEAD模式开始,以访问和使用真实姓名为master
的提交。 (我不知道如何在TortoiseGit中做到这一点。)
如果您具有命令行Git,则可以立即执行此操作-可能应该先完全关闭TortoiseGit,以免它试图撤消它。
请注意,命令行Git会自动“记下”它在每个分支名称下存储的最后几个(或多个)值,Git将该分支称为 reflog 。在命令行中,您可以运行:
051741bc532257903f3563d7d89c69cfdddaaf17
查看此日志的内容。如果您没有在自己的任何位置保存数字git reflog master
,则可能是恢复数字的方法。但是,同样,最好使用分离的HEAD模式检查旧提交。
请注意,在使用分离式HEAD模式获取并检查了一些现有的历史提交之后,您可以创建一个 new 分支名称 at 进行提交,以便进行新的开发从那时开始。为此,请从命令行使用19747382e3680bd90689e998834b492aa66c0730
或git branch
。两者之间的区别在于git checkout -b
首先创建新分支,然后将切换为,以便git checkout -b
包含新分支名称而不是哈希ID。换句话说:
HEAD
等效于:
git checkout -b newbranch
第一步创建分支,在其中存储git branch newbranch
git checkout newbranch
将获得的哈希ID。第二步将该分支名称存储在{em> {em}中,以便git rev-parse HEAD
包含HEAD
。在第二步中,当前签出的提交没有变化,但是当前分支发生了变化。