1. Git?
1.1 Git是什么
Git是目前世界上最先进的分布式版本控制系统
- 集中式版本控制系统:
- 版本库是集中存放在中央服务器的,本地是没有版本库的修改记录的。干活的时候,所以要先从中央服务器取得最新的版本,然后开始干活,干完活了,再把自己的活推送给中央服务器。所以集中式版本控制系统最大的毛病就是必须联网才能工作
- 分布式版本控制系统:
- 分布式版本控制系统根本没有“中央服务器”,每个人的电脑上都是一个完整的版本库,这样,你工作的时候,就不需要联网了,因为版本库就在你自己的电脑上。
- 分布式版本控制系统的安全性要高很多,因为每个人电脑里都有完整的版本库,某一个人的电脑坏掉了不要紧,随便从其他人那里复制一个就可以了
- 分布式版本控制系统通常也有一台充当“中央服务器”的电脑,但这个服务器的作用仅仅是用来方便“交换”大家的修改,没有它也可以继续工作,只服务于交换修改。
2. GIt基础实践
2.1 远程仓库
Git支持多种协议,默认的git://使用ssh协议,但也可以使用https等其他协议。区别:ssh速度相比Https协议快。
- 关联远程库(创建远程库,将本地库和远程库进行关联,两库名要相同)
$ mkdir sduty_0504
$ cd sduty_0504
$ git init
$ touch README.md
$ git add README.md
$ git commit -m "first commit"
$ git remote add origin git@gitee.com:ji-yinchuan/sduty_0504.git
$ git push -u origin "master"
- 克隆远程库(先创建远程库,再克隆远程库到本地)
$ git clone git@gitee.com:jidlke/sduty_0504.git(库地址)
2.2 .git裸仓库探秘
在没有“中央服务器”的支持下,为什么git还可以做版本的控制?
2.2.1 HEAD
HEAD的内容是指向 refs/heads/,指示当前在哪个分支下面
2.2.2 config
config文件存储的配置信息; 仓库url,fetch路径,merge分支。。。。。。
2.2.3 refs
refs里面包含了本仓库所包含的分支 heads 和 tags
- tags (标签,里程碑----git集成了一定版本后,可以打上这个标签 v1.0);
- heads(存放的是所有的分支)
- remotes (提交远程commit的一些信息)
2.2.4 objects
objects 里面包含了对象,分为 tree、commit、blob tree 可以理解为一个文件夹,里面包含了blob, blob 可以理解为是一个具体的文件
git cat-file -t 字符a43a63945 是查看这个哈希值所代表的类型。 git cat-file -p 字符a444a63945 就展示这个哈希值的内容。
2.3 git三大对象
commit、tree 和 blob 三个对象之间的关系 commit: 提交时的镜像 tree: 文件夹 blob: 文件
一个commit里,文件夹是tree类型,文件是blob类型。
tree下面可以包含文件,也就是blob,但是blob没有具体名字,
因为git的存储机制是基于相同文件的内容就认为是同一个blob, 好处:当有多个相同文件时,存储一个,能节省实际的存储空间。
2.4 分离头指针
工作在没有分支的情况下,进行工作,做了很多的变更,生成了很多的commit,当你checkout一个分支的时候,之前进行的变更都会消失,被git垃圾回收。 前提:git checkout commit 场景:试着做修改,改完之后,数据不要的时候,可以使用。
2.5 HEAD即相关技巧
HEAD:指向最新的commit的一个指针。处于分离头状态,就是指向的最新的一个commit,指向分支的时候,就是分支上最新的commit;
比较两个commit的差异:
比较两个commit的差异:
git diff HEAD HEAD^1
git diff HEAD HEAD~2
3. 独自使用git时的常见场景
3.1 四个工作区域
- Workspace:
工作区 ,就是你平时存放项目代码的地方 - Index / Stage:
暂存区 ,用于临时存放你的改动,事实上它只是一个文件,保存即将提交到文件列表信息。对应的 git 命令:git add - Repository:
仓库区(或版本库) ,就是安全存放数据的位置,这里面有你提交到所有版本的数据。其中HEAD指向最新放入仓库的版本。对应的 git 命令:git commit -m ‘desc’ - Remote:
远程仓库 ,托管代码的服务器,可以简单的认为是你项目组中的一台电脑用于远程数据交换。对应的 git 命令:git push
3.2 删除不要的分支
不能在被删除的分支上进行删除
$ git branch -D 分支名
3.3 修改commit的message
修改最新的commit的message
git commit --amend
修改老旧的commit的message
git rebase -i 父类hash值
将第一个单词pick改为r,再保存退出,pick默认是保存这个commit,reword是保存并进行修改
弹出修改message,再进行保存退出
在先弹出的页面第二行填写message信息,
修改几个连续commit的message
git rebase -i 最早的commit的父类hash值
弹出的message信息中,最早的message信息在最上面,message信息前缀还是pick,将后面的修改为s(squash),readme.md文件不变
修改间隔的几个commit的message,整理成1个
进入弹出框后,会看到没有最老的那个commit,
需手动拷贝最老commit的hash值;
将要合并的commit写在这个commit下面,并将pick改为s
在先弹出的页面第二行填写message信息,
git rebase 和 git merge区别:
3.4 版本回退
不断对文件进行修改,进行提交,就会在版本库生成对应的版本信息,
命令进行查看
git log --oneline --all -n3 查看三条记录
git log --pretty=oneline 查看简短记录
回退到上一个版本
git reset --hard HEAD^
查看所有的commit_id
git reflog.
还原原来的版本
git reset --hard commit_id
4. 分支管理
在工作时,会进行很多的变更,生成很多的commit,git将这些变更串成一条时间线,这条时间线就是一条分支。
4.1 创建与合并分支
- 每次提交,Git会把他们串成一条时间线,这条时间线就是一个分支。默认是主分支。Git用master指向最新的提交,再用HEAD指向master,就能确定当前分支,以及当前分支的提交点。也就意味着每一次变更提交,master指针都会随着改变。
新建一个dev分支,也就是增加一个dev指针,修改HEAD的指向。从现在开始,对工作区的修改和提交就是针对dev分支了,比如新提交一次后,dev指针往前移动一步,而master指针不变:
怎么进行分之的合并呢?本质上就是把master指向dev的当前提交,就完成了合并。所以Git合并分支也很快!就改改指针,工作区内容也不变! 也可以删除dev分支。删除dev分支就是把dev指针给删掉,删掉后,也就剩下了一条master分支:
4.2 多人维护分支
- 不同的人修改了不同文件的不同区域
用户A修改了A文件,push远端之前。用户B开始修改B文件,完了之后push远端,之后用户A进行push,会报错,不是fast-forwards关系。所以,用户A需要先git fetch命令进行远端分支的拉取,在用git merge合并代码,在进行push远端。 - 不同的人修改了同文件的不同区域
用户A生成commit,没有push远端,用户B直接做了修改push到远端,用户A不知道用户B做了push,自己也进行了push操作,会报错。所以:因为是同一个文件,可以直接使用git pull命令拉取代码,再次进行push。 - 不同的人修改了同文件的同一区域
假如在index.html文件中同一地方做了更改。用户A生成commit,用户B先进行push操作,用户A在push会报错,应先进行pull操作。在pull之后,会出现提示 Auto–mergeing index.html提示,意思就是说出现冲突了,需要手动进行合并。完了后,在push远端。
Git用<<<<<<<,=======,>>>>>>>标记出不同分支的内容,一般HEAD附近的就是你的代码,下面的分支就是你合并别人的代码。
完结
|