这是一份扼要厄要的Git入门指南,如果你想疾速学会Github,这篇文章是一个不错的抉择。

集体总结,如有不妥之处,敬请指出。

目录

版本库的创立

  • Git的装置
  • 版本库的创立

版本库的操作

  • 文件操作
  • 版本回退
  • 批改撤销

近程库连贯

  • 近程库增加与解除
  • 从近程库克隆

分支治理

  • 创立与合并分支
  • 多人合作

标签治理

  • 创立标签
  • 操作标签

版本库的创立


Git的装置

在Ubuntu Linux上应用apt软件包管理工具进行装置

sudo apt-get install git

在windows上间接进入Git官网下载安装程序,而后依照默认选项装置即可

版本库的创立

抉择一个适合的地位利用mkdir指令创立一个空目录,而后进入后输出指令

git init

于是该目录就变成了Git能够治理的仓库,仔细的读者能够发现当前目录下多了一个.git的目录,这个目录是Git来跟踪治理版本库的,没事千万不要手动批改这个目录外面的文件,不然改乱了,就把Git仓库给毁坏了。

版本库的操作


文件操作

在文件操作之前首先明确几个概念

工作区

就是电脑中能间接看见的目录

版本库

工作区目录中有一个暗藏目录.git。这个是Git的版本库,版本库次要由两个局部组成,stage暂存区和分支区。

将文件增加至Git版本库中时,有三个步骤:

首先在工作区创立一个文件Read.txt

vim/typora Read.txt

将文件批改增加至暂存区,在增加至暂存区前,咱们首先看一下git的状态

~/CS61A$ git statusOn branch masterYour branch is ahead of 'origin/master' by 1 commit.  (use "git push" to publish your local commits)Untracked files:  (use "git add <file>..." to include in what will be committed)    Read.txtnothing added to commit but untracked files present (use "git add" to track)

Git分明的通知咱们,有一个文件呈现了,而Read.txt还素来没有被增加过,所以它的状态是Untracked

而后咱们创立文件这次操作增加至暂存区

git add Read.txt

如果增加的是文件夹能够应用

git add vs/*

如果想删除文件能够用

git rm Read.txt

再次查看git的状态

~/CS61A$ git statusOn branch masterYour branch is ahead of 'origin/master' by 1 commit.  (use "git push" to publish your local commits)Changes to be committed:  (use "git restore --staged <file>..." to unstage)    new file:   Read.txt

Changes to be committed咱们发现git曾经辨认了这个文件,可见这个文件曾经被增加到了暂存区。

最初咱们将文件创建这次操作提交至仓库的master分支(分支的概念前面会讲到)

git commit Read.txt -m "commit"

如果想提交全副文件的操作能够用

git commit -m "commit"

这里的-m参数是对这次提交进行文字说明

再次查看git的状态

~/CS61A$ git statusOn branch masterYour branch is ahead of 'origin/master' by 2 commits.  (use "git push" to publish your local commits)nothing to commit, working tree clean

可见此时暂存区为空,批改已提交至仓库

咱们能够将创立文件并提交至仓库的过程用流程图示意

graph LRA[在工作区创立文件]===>B[将批改/创立/删除操作增加至暂存区]====>C[将操作提交至仓库]

预计很多人都有疑难,为什么这里写的是操作,而不是将文件增加至暂存区,因为Git治理的是批改而不是文件,咱们用一个例子来阐明这个问题。

首先,咱们在Read.txt中增加一段文字hello me,而后将这次操作增加到暂存区,咱们查看此时的状态

it statusOn branch masterYour branch is ahead of 'origin/master' by 2 commits.  (use "git push" to publish your local commits)Changes to be committed:  (use "git restore --staged <file>..." to unstage)    modified:   Read.txt

可见此次批改曾经增加到了暂存区,而后咱们再对文件进行批改,减少一行hello you,不将此次批改增加至暂存区。

git statusOn branch masterYour branch is ahead of 'origin/master' by 2 commits.  (use "git push" to publish your local commits)Changes to be committed:  (use "git restore --staged <file>..." to unstage)    modified:   Read.txtChanges not staged for commit:  (use "git add <file>..." to update what will be committed)  (use "git restore <file>..." to discard changes in working directory)    modified:   Read.txt

咱们执行提交指令将批改提交至仓库,而后查看git状态

git statusOn branch masterYour branch is ahead of 'origin/master' by 8 commits.  (use "git push" to publish your local commits)Changes not staged for commit:  (use "git add <file>..." to update what will be committed)  (use "git restore <file>..." to discard changes in working directory)    modified:   Read.txt

咱们发现,未增加至暂存区的批改并未提交至仓库,咱们查看一下工作区和最新版本库的区别

~/CS61A$ git diff -- Read.txtdiff --git a/Read.txt b/Read.txtindex 1f8eec4..12ee40e 100644--- a/Read.txt+++ b/Read.txt@@ -1,2 +1,3 @@ hello world hello me+hello you

如果Git治理的是文件自身,那么文件在提交时是什么样,提交的文件就是什么样,然而通过比照发现,版本库的文件和工作区的文件是不一样,咱们每次增加到暂存区的是对文件的操作步骤,比方创立删除文件,增加几行,删除几行,因为方才增加hello you这一行文字的批改操作并未增加至暂存区,提交时只提交暂存区有的操作,因而该操作未提交至仓库。

版本回退

下面i讲到,Git治理的是批改,如果咱们在进行批改提交的过程中,不小心删除了最初一行hello me ,而咱们又须要这行文字该怎么办呢?

这时候就须要利用版本回退的性能了。

在Git中,咱们能够查看每次操作的记录

~/CS61A$ git log --pretty=onelineaa03a474011bcb97e9f596d3b5c9a1b517726d05 (HEAD -> master) delete a line05491fda20edff579daf14f24b7afed61d591842 add a linea58d42838b1284034c4a9d52f0d2780ad251bda2 af67db85d1deeb3d7ca0020a332ac4e07bccf12b0 allb96112ab41f972a9949e213347d7403dd2f8a03b 1

咱们要将版本回退到delete a line操作前,因而咱们应用reset指令

~/CS61A$ git reset --hard HEAD^HEAD is now at 05491fd add a line

这里的HEAD^示意上一个版本,如果上两个版本则为^^,以此类推。

然而问题来了,如果咱们当初又想回到delete a line版本该怎么办呢?版本曾经回退了。

git有一个命令记录了你的每次命令

~/CS61A$ git reflog05491fd (HEAD -> master) HEAD@{0}: reset: moving to HEAD^aa03a47 HEAD@{1}: commit: delete a line05491fd (HEAD -> master) HEAD@{2}: commit: add a line

于是咱们就能够利用aa03a47这个id来回到原来版本。

git reset --hard aa03a47HEAD is now at aa03a47 delete a line

于是,版本又回来了。

批改撤销

有的时候咱们会因为手抖写错代码,比方咱们在Read.txt(.sh)文件中增加一行‘rm -rf’,懂点Linux都晓得这是个致命操作。

如果你还没有将这次文件批改提交到暂存区,那么很简略,间接批改就好了,或者也能够应用指令

git checkout -- Read.txt

工作区的批改就被抛弃了,工作区文件的内容和版本库文件的内容雷同。

如果你曾经将文件批改增加到了暂存区,那么咱们须要应用另一个指令

git reset HEAD Read.txt

reset指令不仅能够回退版本,当HEAD不^时,reset指令也能够将暂存区的批改操作移除,而后再利用checkout指令同步版本库和工作区内容。

如果你曾经将批改提交到了版本库,那么依照版本回退的形式进行即可

git reset --hard HEAD^

如果你曾经将版本库内的内容推送到近程库,比方Github,那就只能事在人为了,谁运行,谁遭殃。

近程库连贯


近程库增加/解除

首先,登陆GitHub,而后,在右上角找到“Create a new repo”按钮,创立一个新的仓库

(图借的廖雪峰大L的):

在Repository name填入Read,其余放弃默认设置,点击“Create repository”按钮,就胜利地创立了一个新的Git仓库:

而后,咱们在本地运行命令

 git remote add origin git@github.com:xxxx/Read.git

xxx处为你本人的Github账户名,就能够将本地的版本库和近程的库连接起来了。

将本地库所有内容推送至Github近程库的master分支。

git push (-u) origin master

加上了-u参数,Git岂但会把本地的master分支内容推送的近程新的master分支,还会把本地的master分支和近程的master分支关联起来,在当前的推送或者拉取时就能够简化命令,不许须要退出-u参数。

SSH正告

当你第一次应用Git的clone或者push命令连贯GitHub时,会失去一个正告:

The authenticity of host 'github.com (xx.xx.xx.xx)' can't be established.RSA key fingerprint is xx.xx.xx.xx.xx.Are you sure you want to continue connecting (yes/no)?

这是因为Git应用SSH连贯,而SSH连贯在第一次验证GitHub服务器的Key时,须要你确认GitHub的Key的指纹信息是否真的来自GitHub的服务器,输出yes回车即可。

Git会输入一个正告,通知你曾经把GitHub的Key增加到本机的一个信赖列表里了:

Warning: Permanently added 'github.com' (RSA) to the list of known hosts.

这个正告只会呈现一次,前面的操作就不会有任何正告了。

如果你切实放心有人假冒GitHub服务器,输出yes前能够对照GitHub的RSA Key的指纹信息是否与SSH连贯给出的统一。

解除近程库与本地库的关联关系

如果咱们须要解除本地库与近程库的关联关系,能够应用命令

git remote rm origin

近程库克隆

咱们有时须要把近程库从Github克隆下来,为了借鉴代码或是进行分布式工作,应用以下指令将近程库克隆至本地

git clone git@github.com:xxx/Read.git

分支治理


创立与合并分支

在版本回退里,你曾经晓得,每次提交,Git都把它们串成一条工夫线,这条工夫线就是一个分支。截止到目前,只有一条工夫线,在Git里,这个分支叫主分支,即master分支。HEAD严格来说不是指向提交,而是指向mastermaster才是指向提交的,所以,HEAD指向的就是以后分支。

当咱们创立新的分支,例如dev时,Git新建了一个指针叫dev,指向master雷同的提交,再把HEAD指向dev,就示意以后分支在dev

咱们建设一个新分支dev并切换至新分支

git checkout -b dev    /   git switch -c dev

如果切换至已有分支则

git checkout dev    /    git switch dev

如果只是创立分支

git branch dev

从当初开始,对工作区的批改和提交就是针对dev分支了,比方新提交一次后,dev指针往前挪动一步,而master指针不变:

如果咱们在dev上的工作实现了,就能够把dev合并到master上。Git怎么合并呢?最简略的办法,就是间接把master指向dev的以后提交,就实现了合并:

咱们切换至主分支,而后将dev分支合并至主分支master

git checkout mastergit merge dev

而后咱们能够保留分支,也能够删除分支,如果删除分支

git branch -d dev

多人合作

在理论开发中,咱们应该依照几个根本准则进行分支治理:

首先,master分支应该是十分稳固的,也就是仅用来公布新版本,平时不能在下面干活;

那在哪干活呢?干活都在dev分支上,也就是说,dev分支是不稳固的,到某个时候,比方1.0版本公布时,再把dev分支合并到master上,在master分支公布1.0版本;

你和你的小伙伴们每个人都在dev分支上干活,每个人都有本人的分支,时不时地往dev分支上合并就能够了。

所以,团队单干的分支看起来就像这样:

近程库克隆

团队单干的过程中首先要将近程库克隆至本地,具体形式见前文近程库克隆一节

实现克隆后,Git主动把本地的master分支和近程的master分支对应起来了,默认近程仓库的名称为origin

查看近程库的信息

~/CS61A$ git remote -vorigin    git@github.com:x/CS61A.git (fetch)origin    git@github.com:x/CS61A.git (push)

下面显示了能够抓取和推送的origin的地址。如果没有推送权限,就看不到push的地址。

分支的推送

分支的推送有很多种模式,这里只介绍最简略的模式,假如,咱们曾经将近程库的master分支克隆到了本地,而后咱们创立了一个新的分支dev,在新的分支进行工作,工作结束后咱们将dev分支合并至master分支,而后应用

git push origin master

就将该分支推送到了近程库

分支的抓取

在多人合作时可能会呈现一些问题,比方有一天,你的小伙伴曾经向origin/master分支推送了他的提交,而你碰巧也对同样的文件进行了批改,并试图推送,这时候你会发现,git提醒推送失败,因为你的小伙伴的最新提交和你的提交有抵触。

因而咱们要在推送前先将master最新状况从近程抓下来,而后在本地进行合并和解决抵触。

解决抵触的办法如下

咱们晓得当咱们把近程的master分支抓取下来后,咱们本地的dev分支和近程pull下来的master分支存在抵触

这种状况下,Git无奈执行“疾速合并”,只能试图把各自的批改合并起来,但这种合并会有抵触,咱们查看 一下git的状态

$ git statusOn branch masterYour branch is ahead of 'origin/master' by 2 commits.  (use "git push" to publish your local commits)You have unmerged paths.  (fix conflicts and run "git commit")  (use "git merge --abort" to abort the merge)Unmerged paths:  (use "git add <file>..." to mark resolution)    both modified:   Read.txtno changes added to commit (use "git add" and/or "git commit -a")

Git通知咱们,Read.txt文件存在抵触,咱们能够间接查看文件内容

Git is a distributed version control system.Git is free software distributed under the GPL.Git has a mutable index called stage.Git tracks changes of files.<<<<<<< HEADCreating a new branch is quick & simple.=======Creating a new branch is quick AND simple.>>>>>>> dev

Git用<<<<<<<=======>>>>>>>标记出不同分支的内容,咱们批改如下后保留:

Creating a new branch is quick and simple.
Creating a new branch is quick and simple.

再提交批改给master分支

$ git add readme.txt $ git commit -m "conflict fixed"[master cf810e4] conflict fixed

Git通知咱们抵触被解决了,于是咱们将dev分支合并至master,而后执行push

git push origin masterCounting objects: 6, done.Delta compression using up to 4 threads.Compressing objects: 100% (4/4), done.Writing objects: 100% (6/6), 621 bytes | 621.00 KiB/s, done.Total 6 (delta 0), reused 0 (delta 0)To github.com:x/Read.git   7a5e5dd..57c53ab  master -> master

胜利。

标签治理

为什么须要标签?

Git有commit,为什么还要引入tag?

“请把上周一的那个版本打包公布,commit号是6a5819e...”

“一串乌七八糟的数字不好找!”

如果换一个方法:

“请把上周一的那个版本打包公布,版本号是v1.2”

“好的,依照tag v1.2查找commit就行!”

所以,tag就是一个让人容易记住的有意义的名字,它跟某个commit绑在一起。

创立标签

在Git中打标签非常简单,首先,切换到须要打标签的分支上,而后敲击tag就能够打一个标签

git tag v1.0

利用git tag查看所有标签

$ git tagv1.0v2.0v2.1

如果要对历史commit打标签,那就通过git log找到commit号

git tag v0.9 f287d34

查看每个标签的信息

$ git show v0.9commit f52c63349bc3c1593499807e5c8e972b82c8f286 (tag: v0.9)Author: Michael Liao <askxuefeng@gmail.com>Date:   Fri May 18 21:56:54 2018 +0800    add mergediff --git a/readme.txt b/readme.txt...

而后依照版本回退一节的办法应用reset指令回退至对应版本打包即可。

留神,标签总是和某个commit挂钩。如果这个commit既呈现在master分支,又呈现在dev分支,那么在这两个分支上都能够看到这个标签。

操作标签

如果标签打错了,也能够删除:

$ git tag -d v0.1Deleted tag 'v0.1' (was f15b0dd)

因为创立的标签都只存储在本地,不会主动推送到近程。所以,打错的标签能够在本地平安删除。如果要推送某个标签到近程,应用命令git push origin <tagname>,或应用git push origin --tags推送所有标签。

如果要删除近程标签则先从本地删除标签,而后向近程同步删除指令

$ git push origin :refs/tags/v0.9To github.com:x/Read.gi0t - [deleted]         v0.9

参考

1.菜鸟教程Git

2.廖雪峰的Git教程

3.Git官方网站