本文次要来介绍一下 Git 的外部状态管理系统。它利用基于节点和指针的数据结构来跟踪及治理编辑操作的工夫线。

对本地我的项目而言,任一时刻,Git 处于三种状态中的一种:工作区状态、暂存区状态和提交区状态。
上面利用新建我的项目来演示一下不同状态及其转换。

1. Initialize the project

$ mkdir git_tree_test && cd git_tree_test$ git init提醒:应用 'master' 作为初始分支的名称。这个默认分支名称可能会更改。要在新仓库中提醒:配置应用初始分支名,并打消这条正告,请执行:提醒:提醒:  git config --global init.defaultBranch <名称>提醒:提醒:除了 'master' 之外,通常选定的名字有 'main'、'trunk' 和  'development'。提醒:能够通过以下命令重命名刚创立的分支:提醒:提醒:  git branch -m <name>已初始化空的 Git 仓库于 /Users/phillee/git_tree_test/.git/$ git status位于分支 master尚无提交无文件要提交(创立/拷贝文件并应用 "git add" 建设跟踪) 

这时咱们初始化了一个本地我的项目,默认创立 master 分支,尚无文件跟踪及提交。

2. The Working Directory

$ touch reset_lifecycle_file$ git status位于分支 master尚无提交未跟踪的文件:  (应用 "git add <文件>..." 以蕴含要提交的内容)        reset_lifecycle_file提交为空,然而存在尚未跟踪的文件(应用 "git add" 建设跟踪) 

当初咱们为我的项目新增了文件 reset_lifecycle_file ,尚未提交,以后位于工作区(Working directory)。博客园代码显示零碎太垃圾了,这时的 reset_lifecycle_file 应该是红色的,示意还没有被跟踪。

3. Staging Index

$ git add reset_lifecycle_file $ git status位于分支 master尚无提交要提交的变更:  (应用 "git rm --cached <文件>..." 以勾销暂存)        新文件:   reset_lifecycle_file 

所有变动的文件,Git 都记录在一个区域,叫做"暂存区"(Staging index)。咱们通过 git add 指令将工作区中的内容保留到暂存区,这时曾经实现了对文件的跟踪,但还没有申请提交。这时候的文件曾经被跟踪了,reset_lifecycle_file 应该是绿色的。

4. Commit History

$ git commit -m "init commit"[master(根提交) 88b5382] init commit1 file changed, 0 insertions(+), 0 deletions(-) create mode 100644 reset_lifecycle_file$ git status位于分支 master无文件要提交,洁净的工作区 

暂存区保留变动的文件信息,等到批改完结增加到"提交历史"(Commit history)中,这就相当于以后我的项目的一个快照(snapshot)。
我的项目提交历史就是由不同工夫的快照形成。Git 能够依据此提交信息将我的项目复原到任意一个快照状态。

5. Reverse state switching

后面叙述并展现了三种状态之间的前向转换,当初咱们反过来看一下,如何将以后状态转换成其父状态。

$ touch gitadd_test_file$ vim gitadd_test_file 

新建一个测试文件并利用该文件进行不同状态之间转换的试验。

  • i 键进入编辑模式;
  • 键入 Hello world!
  • esc 退出编辑模式;
  • shift+;进入命令编辑模式;
  • 键入x回车即可保留到文件并退出vim
$ git status位于分支 master未跟踪的文件:  (应用 "git add <文件>..." 以蕴含要提交的内容)        gitadd_test_file提交为空,然而存在尚未跟踪的文件(应用 "git add" 建设跟踪)$ git add gitadd_test_file $ git commit -m "add one file for test"[master d97ee77] add one file for test 1 file changed, 1 insertion(+) create mode 100644 gitadd_test_file$ git log --onelined97ee77 (HEAD -> master) add one file for test88b5382 init commit 

按步骤2-4的形式将新创建的文件增加到提交历史中。当初咱们尝试将曾经提交 commit 但尚未 push 到远端仓库的状态返回到暂存区状态。此时的gitadd_test_file为绿色。

$ git reset --soft 88b538$ git status位于分支 master要提交的变更:  (应用 "git restore --staged <文件>..." 以勾销暂存)        新文件:   gitadd_test_file 

如上后果所示,这时曾经处于 git commit 命令之前的状态,达到此后果应用的是 git reset --soft 指令。
该操作会保留文件的改变及索引状态,撤销实现后将回到增加改变的状态。留神与接下来要应用的 git reset --hard 之间的区别。此时的gitadd_test_file为绿色。

$ git restore --staged gitadd_test_file $ git status位于分支 master未跟踪的文件:  (应用 "git add <文件>..." 以蕴含要提交的内容)        gitadd_test_file提交为空,然而存在尚未跟踪的文件(应用 "git add" 建设跟踪) 

通过 git restore --staged 指令,咱们得以将暂存区状态返回到工作区状态,也就是 git add 之前的状态。此时的gitadd_test_file为红色。

$ git add gitadd_test_file $ git commit -m "add test file for git add test"[master d535a57] add test file for git add test 1 file changed, 1 insertion(+) create mode 100644 gitadd_test_file$ git log --onelined535a57 (HEAD -> master) add test file for git add test88b5382 init commit$ git reset --hard 88b538HEAD 当初位于 88b5382 init commit$ git status位于分支 master无文件要提交,洁净的工作区 

留神这里是将 gitadd_test_file 从新增加到暂存区,而后保留到提交历史中。从提交历史中的状态间接返回到 git add 之前的状态应用的指令是 git reset --hard ,该指令强制将 HEAD 指针指向提交历史线中的前一个提交状态,会连同咱们方才新建的文件一起全副撤销。这是一个比拟危险的行动,应用的时候要留神场合。当然即便这么操作了也并非就不能还原了,只是会多几步操作而已。

(全文完)