Git的基本使用

Git

本文是本人学习廖雪峰的Git教程后的总结

1. Git是分布式版本控制系统

版本控制系统分为分布式和集中式两种

1.1 什么是集中式版本控制系统

集中式版本控制系统,版本库是集中存放在中央服务器的,而工作的时候,都是使用自己的电脑,所以要先从中央服务器取得最新的版本,然后开始工作,工作完了,再把自己的成果推送给中央服务器。

集中式版本控制系统最大的毛病就是必须联网必须联网才能工作!

仅仅只是局域网还好,带宽够大,速度够快。但在互联网上,遇到网速慢的话,可能提交一个10M的文件就需要5分钟。

1.2 Git作为分布式版本控制系统

分布式版本控制系统根本没有“中央服务器”,每个人的电脑上都有一个完整的版本库。这样,你工作的时候,就不需要联网了,因为版本库就在你自己的电脑上。多人协作时,需把各自的修改推送给别人,就可以看到推送者的修改了。

和集中式版本控制系统相比,分布式版本控制系统的安全性要高很多,因为每个人电脑里都有完整的版本库,某一个人的电脑坏掉了不要紧,随便从其他人那里复制一个就可以了。而集中式版本控制系统的中央服务器要是出了问题,所有人都没法干活了。

但是实际应用中,很少在同一局域网工作,因此分布式版本控制系统通常也有一台充当“中央服务器”的电脑,但这个服务器的作用仅仅是用来方便“交换”大家的修改,没有它大家也一样干活,只是交换修改不方便而已。

2. 仓库结构

2.1 工作区

工作区就是我们电脑本地能看到的文件

.git是隐藏文件夹,里面是记录版本库的信息,不要去修改它,以免版本库损坏

2.2 版本库

(图片来源网络,侵删)

版本库图解

HEAD是一个指向master分支(它也是一个指针,这个指针的指向是当前版本)的一个指针)

3. Git管理的是修改,而不是文件本身

3.1 创建一个Git本地仓库

会用到的一些语法

$ cd <path>
// 跳转到<path>路径下

$ mkdir <name>
// 当前目录下创建一个名为<name>的文件夹

$ git init
// 将当前目录初始化为本地仓库

例如:

我的电脑 MINGW64 /g/warehouse
$ mkdir test

我的电脑 MINGW64 /g/warehouse
$ cd test

我的电脑 MINGW64 /g/warehouse/test
$ git init
Initialized empty Git repository in G:/warehouse/test/.git/

首先创建一个test文件夹,然后跳转到此目录下,将其初始化为本地仓库

3.2 管理修改

会用到的一些语法

$ touch <filename.***>
// 创建文件<filename.***>

$ vi <filename.***>
// 使用vi编辑器编辑文件,具体操作自行查阅

$ git add <filename.***>
// 添加文件到暂存区

$ git status
// 查看暂存区状态

$ git commit -m "<commit message>"
// 提交暂存区到分支,每次提交写上"<commit message>"是个好习惯

例如

我的电脑 MINGW64 /g/warehouse/test (master)
$ touch README.md

我的电脑 MINGW64 /g/warehouse/test (master)
$ vi README.md

我的电脑 MINGW64 /g/warehouse/test (master)
$ git add README.md

我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master

No commits yet

Changes to be committed:
  (use "git rm --cached <file>..." to unstage)
        new file:   README.md


我的电脑 MINGW64 /g/warehouse/test (master)
$ git commit -m "add README.md"
[master (root-commit) 48711df] add README.md
 1 file changed, 1 insertion(+)
 create mode 100644 README.md
 
我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master
nothing to commit, working tree clean

3.3 撤销修改

会用到的一些语法

$ git checkout -- <filename.***>
// 撤销<filename.***>的修改

$ git reset HEAD <filename.***>
// 已经add时,将<filename.***>返回到版本库状态,再使用git checkout -- <filename.md>

例如

3.3.1 未add到暂存区时
我的电脑 MINGW64 /g/warehouse/test (master)
$ git checkout -- README.md

还未add时,只需使用git checkout -- <filename.***>撤销<filename.***>的修改

3.3.2 已经add到暂存区
我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master
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:   README.md

no changes added to commit (use "git add" and/or "git commit -a")

我的电脑 MINGW64 /g/warehouse/test (master)
$ git add README.md
warning: LF will be replaced by CRLF in README.md.
The file will have its original line endings in your working directory

我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master
Changes to be committed:
  (use "git restore --staged <file>..." to unstage)
        modified:   README.md


我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master
Changes to be committed:
  (use "git restore --staged <file>..." to unstage)
        modified:   README.md


我的电脑 MINGW64 /g/warehouse/test (master)
$ git reset HEAD README.md
Unstaged changes after reset:
M       README.md

我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master
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:   README.md

no changes added to commit (use "git add" and/or "git commit -a")

我的电脑 MINGW64 /g/warehouse/test (master)
$ git checkout -- README.md

已经add时使用git reset HEAD <filename.***>将<filename.***>返回到版本库状态,使用git checkout -- <filename.md>

3.4 删除文件

会用到的一些语法

$ git rm <filename.***>
// 移除文件<filename.***>

例如

// 新建一个文件test.md,并提交到版本库
我的电脑 MINGW64 /g/warehouse/test (master)
$ touch test.md

我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master
Untracked files:
  (use "git add <file>..." to include in what will be committed)
        test.md

nothing added to commit but untracked files present (use "git add" to track)

我的电脑 MINGW64 /g/warehouse/test (master)
$ git add test.md

我的电脑 MINGW64 /g/warehouse/test (master)
$ git commit -m "add test.md"
[master a633db8] add test.md
 1 file changed, 0 insertions(+), 0 deletions(-)
 create mode 100644 test.md


// 下面是删除此文件
我的电脑 MINGW64 /g/warehouse/test (master)
$ git rm test.md
rm 'test.md'

我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master
Changes to be committed:
  (use "git restore --staged <file>..." to unstage)
        deleted:    test.md


我的电脑 MINGW64 /g/warehouse/test (master)
$ git commit -m "delete test.md"
[master 9c1123e] delete test.md
 1 file changed, 0 insertions(+), 0 deletions(-)
 delete mode 100644 test.md

我的电脑 MINGW64 /g/warehouse/test (master)
$ git status
On branch master
nothing to commit, working tree clean

移除之后需要git commit提交到版本库,若是误删且还未提交到版本库,即可使用git checkout -- <filename.***>恢复

4. 远程仓库

4.1 关联远程仓库

$ git remote add origin git@github.com:<your username>/learngit.git

4.2 推送到远程仓库

$ git push -u origin master

由于远程库是空的,我们第一次推送master分支时,加上了-u参数,Git不但会把本地的master分支内容推送的远程新的master分支,还会把本地的master分支和远程的master分支关联起来,在以后的推送或者拉取时就可以简化命令。

后面的推送:

$ git push origin <name>
// 推送到<name>分支

4.3 从远程仓库克隆

$ git clone git@github.com:<your username>/gitskills.git

注意:这里克隆下来的只有master分支,若要在其他分支上开发,必须创建远程origin<name>分支到本地

$ git checkout -b <name> origin/<name>

5. 分支管理

5.1 创建与合并分支

会用到的语句:

$ git branch
// 打印所有分支,*代表当前分支

$ git branch -d <name>
// 删除<name>分支,前提时已经合并的分支

$ git branch -D <name>
// 强行删除<name>分支,同于未被合并的分支

$ git switch <name>
// 切换到已有的分支<name>

创建时使用语句:

$ git branch <name>
$ git checkout <name>
// 创建名为<name>的分支,并切换到<name>分支

$ git checkout -b <name>
// 此句与上两句等效

$ git switch -c <name>
// 但是Git更鼓励使用此语句

合并时使用的语句:

$ git merge <name>
// 快速合并(Fast-forward),将当前分支合并到<name>分支,但是一旦删除<name>分支,就会失去分支信息

$ git merge --no-ff -m "merge with no-ff" <name>
// 禁用Fast-forward的合并,同时会commit,即便分支删除,也会保留分支信息

查看合并历史

$ git log --graph --pretty=oneline --abbrev-commit

5.2 快照

会用到的语句:

$ git stash
// 将当前的工作现场储存起来

$ git stash apply
// 恢复工作现场

$ git stash drop
// 删除之前储存的工作现场

$ git stash pop
// 恢复工作现场的同时删除之前储存的工作现场

5.3 解决冲突

为什么会冲突呢?很简单,两个分支从一个起点出发,向着两个不同的方向并行,要合并时两个分支的内容不一样,比如同一个文件的内容时不一样的,此时Git会告诉你合并冲突了,要你手动修改以解决冲突。

Git用<<<<<<<=======>>>>>>>标记出不同分支的内容,我们进行选择性的修改就行

5.4 分支策略

在实际开发中,我们应该按照几个基本原则进行分支管理:

首先,master分支应该是非常稳定的,也就是仅用来发布新版本,平时不能在上面干活;

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

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

添加一个新功能时,你肯定不希望因为一些实验性质的代码,把主分支搞乱了,所以,每添加一个新功能,最好新建一个feature分支,在上面开发,完成后,合并,最后,删除该feature分支。

所以,团队合作的分支看起来就像这样:(引用廖雪峰的图)

git-br-policy

哪些分支需要推送,哪些不需要呢?

  • master分支是主分支,因此要时刻与远程同步;
  • dev分支是开发分支,团队所有成员都需要在上面工作,所以也需要与远程同步;
  • bug分支只用于在本地修复bug,就没必要推到远程了,除非老板要看看你每周到底修复了几个bug;
  • feature分支是否推到远程,取决于你是否和你的小伙伴合作在上面开发。

5.5 Rebase(变基)

还没有领略其中的奥义,大佬们可以看看廖雪峰大神的.

6. 标签管理

会用到的语句:

$ git tag <name>
// 创建新标签,默认打在最新的一次commit上

$ git tag
// 查看所有标签,注意,标签不是按时间顺序列出,而是按字母排序的。

$ git tag <name> <commit id>
// 给<commit id>打上标签<name>

$ git show <name>
// 显示标签的信息

$ git tag -d <name>
// 删除标签,因为创建的标签都只存储在本地,不会自动推送到远程。所以,打错的标签可以在本地安全删除

$ git push origin <name>
// 推送某个标签到远程

$ git push origin --tags
// 推送所有未推送的标签到远程

$ git push origin :refs/tags/<name>
// 删除一个远程标签,先从本地删除

7. 命令行小结

7.1 文件管理

显示当前路径

$ pwd

新建文件

$ touch <filename.***>

编辑文件(使用vi编辑器,关于vi的命令行自行查阅)

$ vi <filename.***>

新建文件夹

$ mkdir <name>

将当前目录初始化为本地仓库

$ git init

跳转

返回上一级的 <path>..

$ cd <path>

添加文件到暂存区

$ git add <filename.***>

从暂存区移除文件

$ git rm --cache <filename.***>

查看暂存区状态

$ git status

提交暂存区到版本库

$ git commit -m "<commit message>"

7.2 打印日志(git log 类)

$ git log 
// 打印日志,内容繁多

$ git log --pretty=oneline
// 打印简单的日志

$ git reflog
// 打印所有的日志,包括被删除的

$ git log --graph --pretty=oneline --abbrev-commit
// 打印分支信息

7.3 远程仓库

关联远程的新仓库

$ git remote add origin git@github.com:<your username>/<name>.git

第一次推送到远程仓库

$ git push -u origin master

后期的推送

$ git push origin <name>

将远程仓库克隆到本地(默认master分支)

git clone git@github.com:<your username>/<name>.git

注意:这里克隆下来的只有master分支,若要在其他分支上开发,必须创建远程origin<name>分支到本地

$ git checkout -b <name> origin/<name>

拉取最新的提交

$ git pull

可能会失败,因为没有建立分支于远程分支的链接,命令如下

$ git branch --set-upstream-to=origin/<name> <name>

7.4 分支

打印所有分支,*代表当前分支

$ git branch

创建时使用语句:

$ git branch <name>
$ git checkout <name>
// 创建名为<name>的分支,并切换到<name>分支

$ git checkout -b <name>
// 此句与上两句等效

$ git switch -c <name>
// 但是Git更鼓励使用此语句

合并时使用的语句:

$ git merge <name>
// 快速合并(Fast-forward),将当前分支合并到<name>分支,但是一旦删除<name>分支,就会失去分支信息

$ git merge --no-ff -m "merge with no-ff" <name>
// 禁用Fast-forward的合并,同时会commit,即便分支删除,也会保留分支信息

删除<name>分支,前提时已经合并的分支

$ git branch -d <name>

强行删除<name>分支,同于未被合并的分支

$ git branch -D <name>

切换到已有的分支<name>

$ git switch <name>

临时储存还未提交的分支

$ git stash
// 将当前的工作现场储存起来

$ git stash apply
// 恢复工作现场

$ git stash drop
// 删除之前储存的工作现场

$ git stash pop
// 恢复工作现场的同时删除之前储存的工作现场

7.5 标签

创建新标签,默认打在最新的一次commit上

$ git tag <name>

查看所有标签,注意,标签不是按时间顺序列出,而是按字母排序的

$ git tag

给打上标签

$ git tag <name> <commit id>

显示标签的信息

$ git show <name>

删除标签,因为创建的标签都只存储在本地,不会自动推送到远程。所以,打错的标签可以在本地安全删除

$ git tag -d <name>

推送某个标签到远程

$ git push origin <name>

推送所有未推送的标签到远程

$ git push origin --tags

删除一个远程标签,先从本地删除

$ git push origin :refs/tags/<name>
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值