Git 为什么除了最后一个,所有的承诺都消失了?
我对git是个新手。5天前,我通过以下命令在本地文件夹(名为myproject)上初始化了git:Git 为什么除了最后一个,所有的承诺都消失了?,git,github,Git,Github,我对git是个新手。5天前,我通过以下命令在本地文件夹(名为myproject)上初始化了git: $ git init $ git add . $ git commit -m "my first commit" $ git push -u origin master $ git push -f origin {token}:master 此外,我还通过以下命令将所有文件夹/文件(存在于myproject文件夹中)添加到stage: $ git init $ git add . $
$ git init
$ git add .
$ git commit -m "my first commit"
$ git push -u origin master
$ git push -f origin {token}:master
此外,我还通过以下命令将所有文件夹/文件(存在于myproject文件夹中)添加到stage:
$ git init
$ git add .
$ git commit -m "my first commit"
$ git push -u origin master
$ git push -f origin {token}:master
然后通过以下命令提交:
$ git init
$ git add .
$ git commit -m "my first commit"
$ git push -u origin master
$ git push -f origin {token}:master
之后,我为它设置了一个遥控器:
$ git remote add origin https://...
然后通过以下命令将所有内容推送到github上的我的存储库中:
$ git init
$ git add .
$ git commit -m "my first commit"
$ git push -u origin master
$ git push -f origin {token}:master
从5天前到昨天,我又提交了7次更改 注意:所以直到昨天我才提交了8次
今天,我试图获得一些关于git命令的新体验,现在令人惊讶的是,我只面临一个提交(只有最后一个存在,以前所有的提交都消失了)。老实说,我不知道我做了什么。但我怀疑这个命令:
$ git init
$ git add .
$ git commit -m "my first commit"
$ git push -u origin master
$ git push -f origin {token}:master
它是否会删除除最后一次提交之外的所有其他提交?如果没有,你知道我做了什么吗?(我想知道这一点,因为我想避免再次这样做)
编辑:我不确定这是否重要,但当我玩命令时(为了获得经验),我还通过
签出创建了一个分支
git push-f是否会删除[some]提交
可能是的。这完全取决于你推什么
今天,我试图获得一些关于git命令的新体验,现在令人惊讶的是,我只面临一个提交(只有最后一个存在,以前所有的提交都消失了)
首先,让我们注意到Git非常努力地不放弃任何提交,所以您可能还可以(只要您没有从.Git
目录本身中删除文件)
第二,让我们快速看看如何工作。
在Git中,提交本身是一个相当小的对象。下面是一个来自Git存储库的Git自身提交示例(但将@
替换为
):
如您所见,此树
依次引用blob
s,它们是保存文件内容的Git对象。这就是提交存储文件的方式:它有一个树
,树
有blob
s,可能还有更多的tree
s,而blob
s给出了文件对象ID和签出提交时在工作树中使用的名称
不过,这里要重点关注的关键一行是父行。该行给出了另一个提交的ID
Git反向工作
Git使用这些parent
id(从新提交到旧提交)来构建Git所称的“提交图”,或DdirectedAcyclicGraph或DAG。我们可以自己绘制这个DAG,用表示提交的圆形o
替换每个丑陋的SHA-1哈希ID:
o <- o <- o <-- master
这些都在您的存储库中,虽然我这次没有画内部箭头,H
指向G
,它指向F
,依此类推到A
如果你做了不止一个分支,你会得到需要画不止一条线的东西。例如,假设您在master
上通过E
提交A
,但随后运行git checkout-b-side
以创建名为side
的新分支:
A--B--C--D--E <-- master, HEAD->side
现在side
指向H
,而master
仍然指向E
。如果您git checkout master
并运行git log
,git将首先读取HEAD
(现在将指向master
,而不是side
),然后读取commitE
,然后返回A
,您将只看到五次提交,而不是全部八次提交
如果运行git log-side
,您将看到所有八个提交。这是因为git log
不会从头开始,而是从侧开始,它指向H
。请注意,F
仍然指向E
,因此日志从侧
平稳过渡到主
。事实上,此时提交A
到E
在两个分支上
如果现在删除名称侧
,则会发生以下情况:
A--B--C--D--E <-- master
\
F--G--H <-- HEAD->side
A--B--C--D--E <-- HEAD->master
\
F--G--H [abandoned]
这在您的存储库中。但是其他地方还有另一个独立的Git存储库,特别是在您称之为origin
的机器上。该Git存储库有一些提交集和一些分支名称,这些名称指向每个分支的提示提交。正如您的主机
指向提交H
,它们的主机也指向一些提交
如果运行git push
而不运行-f
--f
是“force”标志,也可以拼写为-force
,这样您就可以执行git push原始主机
,那么您的git会将您的提交发送到他们的git,1然后礼貌地询问他们,如果他们愿意,请将他们的主机设置为指向提交H
,就像您的一样
如果他们的master
指向H
左侧的某个地方(即,指向A-B-C-…-G
)中的任何提交,那么让他们的master
指向新的H
提交是非常安全的,因为H
指向G
,G
指向F
,依此类推回到A
。这意味着他们不会“丢失”任何提交。(从他们的master
指向的任何地方到H
的动作称为快进操作。)但如果他们有一些你没有的其他承诺,那么他们的master
指向其他东西,即使有点不同,他们也会拒绝你的礼貌请求,因为那样会失去工作。例如,假设