精通Git(三)——Git分支机制

news2024/11/15 12:15:57

文章目录

  • 前言
  • 分支机制简述
    • 创建分支
    • 切换分支
  • 基本的分支与合并操作
    • 基本的分支操作
    • 基本的合并操作
    • 基本的合并冲突处理
  • 分支管理
  • 与分支有关的工作流
    • 长期分支
    • 主题分支
  • 远程分支
    • 推送
    • 跟踪分支
    • 拉取
    • 删除远程分支
  • 变基
    • 基本的变基操作
    • 变基操作的潜在危害
    • 只在需要的时候执行变基操作
    • 变基操作与合并操作的对比
  • 总结


前言

几乎每个版本控制系统都支持某种形式的分支功能。分支意味着偏离开发主线并继续你自己的工作而不影响主线开发。在很多版本控制工具中,这么做存在着比较昂贵的成本,因为常常需要去对整个源代码目录进行一次复制,而对于大型项目,这种复制会耗去很长时间。
而Git很好的解决了这个问题,怎么做的?看下面的博客你就懂了。

分支机制简述

要想真正理解Git分支机制,我们要首先回过头来看一下Git是如何存储数据的。
正如前面的博客所言,Git并没有采用变更集(changeset)或是差异的方式存储数据,而是采用一系列快照的方式。
当你发起提交时,Git存储的是提交对象,其中包含了指向存储区快照的指针。提交对象也包括作者姓名和邮箱地址、已输入的提交信息以及指向其父提交的指针。初始提交没有父提交,而一般的提交会有一个父提交;对于两个或多个分支的合并提交来说,存在着多个父提交。
在这里插入图片描述

现在Git仓库中有5个对象:3个blob对象(分别保存了你的三个文件的内容)、1个树对象(记录着目录结构以及blob对象和文件名之间的关系),以及一个提交对象(包含着提交的全部元数据和指向根目录树对象的指针)

Git分支只不过是一个指向某次提交的轻量级的可移动指针。Git默认的分支名是master。当你发起提交时,就有了一个指向最后一次提交的master分支。每次提交它都会自动向前移动。

创建分支

创建分支
git branch branch_name
在这里插入图片描述

查看各个分支当前所指向的对象。
git log --oneline --decorate
在这里插入图片描述

切换分支

操作如下
在这里插入图片描述
以上的命令一共做了两件事。他会把HEAD指针(Git的HEAD指针不同于其他版本控制系统,是一个指向当前所在的本地分支的指针
移回到master分支,还会把工作目录的文件恢复到master分支指向的快照的状态。这也就意味着,从这时起,你所做的修改将基于项目的较老版本。总而言之,上述操作回滚了你在testing分支上所做的工作,使你能向另一个方向进行开发工作。
在这里插入图片描述

当你准备好了就可以合并这些修改(见后文)
Git中的分支实际上就是一个简单的文件,其中包含了该分支所指向提交的长度为40个字符的SHA-1校验和。正因如此,Git分支创建和删除的成本很低。而且Git提交时保存了父对象的指针,当进行合并操作时Git会自动寻找合适的合并基础,操作起来非常简单。

基本的分支与合并操作

现在我们要展示一个简单的分支和合并案例,其中的工作流可供真实项目借鉴。要遵循的步骤如下:

  • 在网站上开展工作;

  • 为新需求创建分支;

  • 在新分支上展开工作;
    这时,你接到一个电话,说项目有一个很严重问题需要紧急修复。你随后会这样做:

  • 切换到你的生产环境分支;

  • 创建新的分支进行此次问题的热修补工作;

  • 通过测试后,合并热修补分支并推送到生产环境中;

  • 切换回之前的需求分支上继续工作。

基本的分支操作

操作如下
在这里插入图片描述

现在,你接到一个电话,说网站突然有个问题需要立即修复。如果没有Git的帮助,你要么把你的修复补丁和issu53的变更一起部署,要么就花费大量精力去恢复之前针对的issu53所做的工作,好让你制作的修复补丁单独上线。如今你要做的就是切换回master分支即可。
但先别急,在你切换分支之前要注意的是,如果你的工作目录或者暂存区存在着未提交的更改,并且这些更改与你要切换的分支冲突。Git就会不允许你切换分支。在切换分支时,最好是保持一个干净的工作区域。后面我们会介绍几种绕过这个问题的办法:存储和修改提交。就现在而言,让我们假定你已经提交了所有更改,操作如下
在这里插入图片描述在这里插入图片描述

然后删除hotfix分支,切回issu53分支,继续我们的工作
在这里插入图片描述
继续操作如下
在这里插入图片描述
值得注意的是,issu53分支并不包含你在hotfix分支上做的操作。如果需要上述修补工作并入issu53,就需要执行git merge master使得master分支合并到issu53中,或者可以等到要把issu53合并回master分支时再把热修补的工作整合进来。

基本的合并操作

现在issu53的工作已经完成,我们需要合并回主分支。操作如下
git checkout master
git merge issu53
在这里插入图片描述

与之前简单的向前移动分支指针不同,这次Git会基于三方合并的结果创建一个新的快照,然后创建一个提交指向新的快照。这个提交叫做合并提交“。合并提交的特殊性在于它拥有不止一个父提交”
删除issu53分支
在这里插入图片描述

基本的合并冲突处理

有时候,上述合并过程并不会那么顺利。如果你在要合并的两个分支上都改了同一个文件的同一部分内容,Git就没办法干净的合并这两个分支。如下
在这里插入图片描述
在这里插入图片描述

你只需要进入将文件删除,修改成你想要的那样就可以解决了。然后再次合并就OK。
你也可以使用图形化工具来解决冲突git mergetool.
在这里插入图片描述

冲突解决后,相应的文件就进入了暂存区,然后使用git commit命令来完成此次合并提交。
在这里插入图片描述

分支管理

前面我们已经分析了git branch 与 git branch -v。另外还有两个很有用的选项是--merged--no-merged。这两个选项分别是筛选已并入当前分支的所有分支和筛选尚未并入的所有分支。
查看那些分支已经并入当前分支:
git branch --merged
查看那些分支没有并入到当前分支:
git branch --no-merged
在这里插入图片描述
注意:如果你没有合并到当前分支,是不能直接删除的,如果实在想删除就使用-D选项
在这里插入图片描述

与分支有关的工作流

长期分支

长期分支指的是在较长时间内多次把一个分支合并到另一个分支上去,而合并的这个分支就用来存放发放版本的代码。
很多使用Git的开发者都喜欢构建他们自己的工作流。例如,其中一种流程就是master分支只存放稳定版本的代码,即已经发布的版本或即将发布的版本的代码。他们还会使用另一个叫做develop或 next的平行分支用于开发,或是用于测试代码的稳定性。

主题分支

与长期分支不同,在任何规模的项目上主题分支都非常有用。主题分支是指短期的,用于实现某一特定的功能及其相关工作的分支。

远程分支

远程分支指的是指向远程仓库的分支指针,这些指针存在于本地且无法被移动。当你与服务器进行任何网络通信时,他们会自动更新。远程分支有点像书签,他们会提示你上一次连接服务器时远程仓库中每个分支的位置。
使用git fetch xxx 命令将远程服务器的数据同步到本地

推送

当需要同别人共享某个分支上的工作成果时,就要把它推送到一个具有写权限的远程仓库。你的本地分支并不会自动同步到远程仓库,必须要显式地推送那些你想与别人共享的分支。
使用git push (remote) (branch)命令即可。
如果不想每次推送时都键入密码,可以设置一个“凭据缓存”。最简单的设置方式就是把凭据信息暂时保存在内存中几分钟,这只需要执行git config --global credential.helper cache命令即可。

跟踪分支

基于远程分支创建的本地分支会自动成为跟踪分支,或者有时候也叫做游分支。
跟踪分支是远程分支直接关联的本地分支。如果

拉取

git fetch命令会拉取本地没有的远程所有最新更改数据,但这条命令完全不会更改你的工作目录。它只会从服务器上读取数据,然后让你自己进行合并。初次之外,还有一个git pull命令,这条命令在大多数情况下基本等同于git fetch + git merge

删除远程分支

当你和你的同事已经完成一个功能,并且把工作合并到了远程的master分支之后,你已经不再需要包含这个功能的远程分支了。可以通过git push --delete选项来删除远程分支。
基本上可以说,以上命令只是删除了远程服务器上的分支指针。Git会保留数据一段时间,直到下一次触发垃圾回收。所以,即使误删了分支,一般来说也很容易进行恢复。

变基

在Git中,要把更改从一个分支整合到另一个分支,有两种主要方式:合并和变基。

基本的变基操作

之前我们讲过,要整合不同的分支,最简单的办法就是使用merge命令。该命令会对两个分支上的最新提交快照以及这两个提交快照最近的共同祖先,进行一次三方合并,并创建一个新的合并提交。实际上,除了上述方式之外还有一种方式:你可以把另一个分支的提交的更改以补丁的形式应用到另一个分支上。这种操作就叫做变基。使用如下命令
git checkout xxx
git rebase master
变基的工作原理是:首先找到两个要整合的分支(你当前的分支和要整合到的分支)的共同祖先,然后取得当前所在分支的每次提交引入的更改(diff),并把这些更改保存为临时文件,这之后将当前分支重置为要整合的分支,最后在该分支上依次引入之前保存的每个更改。
总结:
变基就是把某条开发分支线上的工作在另一个分支线上按顺序重现。而合并操作则是找出两个分支的末端,并把他们合并在一起。

变基操作的潜在危害

变基操作可以带来种种好处。但它并不是完美无缺、其缺点可以总结成一句话:不要对已经存在于本地仓库之外的提交执行变基操作。——即不要对已经推送到远程服务器的公开提交进行变基操作。
这是因为在执行变基操作时,实际上是抛弃了已有的某些提交,随后创建了新的对应提交。

只在需要的时候执行变基操作

如果你将变基操作看作在推送数据前整理和处理提交的一个手段,并且你只对那些仅存在于本地还没有公开的提交进行变基操作,那么一切都不会有问题。反之,如果你对那些已经推送了的提交执行变基操作,而这时其他人可能已经基于这些提交进行了自己的开发工作,那么那就可能会遇到大麻烦,使用git pull --reabse = git fetch + git rebase remote/branch来减轻你的痛苦。

变基操作与合并操作的对比

区别:合并不会更改实际的历史记录,变基则会更改历史记录。结合这两种操作的优点的操作方式是,对本地尚未推送的更改进行变基操作,从而简化提交历史,但绝不能对任何已经推送到服务器的更改进行变基操作。

总结

相信现在你应该可以自由创建和切换到新的分支,在不同的分支之间切换,并对本地的不同分支进行合并操作。你也应该可以将你的分支推送到远程服务器来分享你的工作成果,与其他人在某个分支上进行协作,对本地尚未推送的分支进行变基操作。
后面将对如何搭建自己的Git仓库托管服务器进行分析和学习。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1812.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

C++——vector容器的基本使用和模拟实现

1、vector的介绍 vector是表示可变大小数组的序列容器。 就像数组一样,vector也采用的连续存储空间来存储元素。也就是意味着可以采用下标对vector的元素 进行访问,和数组一样高效。但是又不像数组,它的大小是可以动态改变的,而且…

【动手学深度学习PyTorch版】18 使用块的网络 VGG

上一篇请移步【动手学深度学习PyTorch版】17 深度卷积神经网络 AlexNet_水w的博客-CSDN博客 目录 一、使用块的网络 VGG 1.1 AlexNet--->VGG ◼ VGG网络简介 1.2 VGG架构 1.3 总结 二、VGG网络的代码实现 2.1 VGG网络(使用自定义) 一、使用块的…

软件测试基本概念

目录本章要点什么是软件测试?软件测试的特定?软件测试和开发的区别?软件测试和软件开发中的调试有什么区别?软件测试在不同公司的定位?一个优秀的测试人员应该具备的素质(你为啥要选择测试开发)需求是衡量软件测试的依据从软件测试人员角度看需求为啥需求对软件测试人员如…

SpringBoot 面试题总结 (JavaGuide)

SpringBoot 面试题总结 (JavaGuide) 用 JavaGuide 复习 SpringBoot 时,找到一些面试题,没有答案,自己花了一天时间在网上找资料总结了一些,有些答案的来源比较杂忘了没有标注,望见谅。 1. 简单…

Visual Studio 2022开发Arduino详述

目录: 一、概述 二、软件的下载与安装 1、前言 2、Visual Studio 2022的下载与安装 3、Visual Micro扩展插件的导入 4、Visual Micro的使用 1)安装修改插件 2)搜索 : Visual.Micro.Processing.Sketch.dll 3)打开Visual.…

【Linux学习】基础IO

目录前言一、C语言文件IO1. C语言文件接口以及打开方式2. 对当前路径的理解3. 默认打开的三个流二、 系统文件IO1. 系统接口openwritereadclose系统接口和库函数2. 文件描述符及其分配规则文件描述符文件描述符分配原则3. 重定向及dup2系统调用重定向标准输出和标准错误的区别d…

Linux XWindow的安装和配置

1.开始安装XWindow必须需要的组件 输入指令:yum groupinstall "X Window System" yum groupinstall "X Window System" 选择y继续安装。 当看到complete表示已经安装成功了。 输入startx测试一下 看到如上界面就证明你的XWindow安装成功了。 2…

Python数据分析(3):pandas

文章目录二. pandas入门2.1 数据结构2.1.1 Series对象2.1.2 DataFrame对象2.2 读取数据2.2.1 读取Excel:read_excel()1. 读取特定工作簿:sheet_name2. 指定列标签:header3. 指定行标签:index_col4. 读取指定列:usecols…

TypeScript接口——interface

目录 一、接口概述: 二、接口类型介绍: 1、属性接口: 2、 函数接口: 3、可索引接口: (1)可索引接口约束数组示例: (2) 可索引接口约束对象示例&#xf…

【Python】numpy矩阵运算大全

文章目录前言0 遇事不决,先查官网,查着查着就查熟了1 矩阵运算及其必要性2 矩阵的创建2.1 普通矩阵2.2 特殊矩阵3 矩阵的索引3.1 str, list, tupple的索引3.2 numpy索引4 矩阵的运算4.1 通用函数与广播机制4.3 矩阵乘法4.4 矩阵求逆4.5 矩阵转置4.6 向量…

SpringBoot整合mybatis-plus 实现增删改查和分页查询

SpringBoot整合mybatis-plus 实现增删改查和分页查询整体的运行图片:一、环境搭建:1、依赖2、application.yml文件3、数据库二、实体类:三、数据层开发——基础CRUD四、业务层开发——分页功能制作4.1分页配置类 configuration4.2service接口…

【Node.js】模块化学习

Node.js教学 专栏 从头开始学习 目录 模块化的基本概念 什么是模块化 现实中的模块化 编程领域中的模块化 模块化规范 Node.js中的模块化 Node.js中模块的分类 加载模块 Node.js中的模块作用域 什么是模块作用域 模块作用域好处 向外共享模块作用域中的成员 module对象 modu…

第二站:分支与循环(终幕)一些经典的题目

目录 一、计算n的阶乘 1.一般解法 2.优化不能表示出较大数的阶乘 二、 计算 1!2!3!……10! 1.循环嵌套解法 2.一次循环解法(优化计算时间) 三、在一个有序数组中查找具体的某个数字n 1.遍历查找 2.二分查找算法(优化了查找时间) 四、编写代码&am…

IDEA Out of memory 问题

文章目录1. 前提2. 问题记录与解决方案1. 前提 阅读本文之前,读者要首先把 Out of memory 这个问题的解决方案多搜几个帖子,先按照其他帖子的解决方案(修改配置文件Xmx属性等)尝试一遍,不能解决再参考本文。 本文所描…

前端小游戏——植物大战僵尸

给大家分享一个植物大战僵尸网页游戏源代码,感兴趣的小伙伴可收藏学习 👉完整源码 文章目录⌛️效果展示⌛️游戏介绍⌛️游戏内容(1)冒险模式(2)小游戏⌛️图片资源⌛️代码展示(1)…

【黑猩猩算法】基于加权反对技术和贪婪搜索进化黑猩猩优化算法求解多模态工程问题附matlab代码

✅作者简介:热爱科研的Matlab仿真开发者,修心和技术同步精进,matlab项目合作可私信。 🍎个人主页:Matlab科研工作室 🍊个人信条:格物致知。 更多Matlab仿真内容点击👇 智能优化算法 …

终于拿到了阿里P8架构师分享的JCF和JUC源码分析与实现笔记java岗

时代的一粒尘,落在每个人身上,就是一座山”。 时代更迭变换,我们好像都知道今天与昨天不同,又好像肉眼看不出哪里不同。 但其实它就正在以各种各样的方式体现在每一个普通人身上。 疫情爆发三个月的时间,截止2020年…

~外中断~

目录 一、接口芯片和端口 二、外中断信息 三、PC机键盘的处理过程 一、接口芯片和端口 外设的输出不直接送入内存和CPU,而是送入相关的接口芯片的端口中;CPU向外设的输出也不是直接送入外设,而是先送入端口,再由相关的芯片送到…

C语言程序设计--火车订票系统

任务要求: 创建一个火车票管理系统,功能包括: (1)录入班次信息(信息用文件保存),可不定时地增加班次数据 (2)浏览班次信息,可显示出所有班次当前状总(如果当前系统时间超过了某班 次的发车时间,则…

js中map()的使用详解

引入: 有网友有如下困惑: map是数组的方法,有一个参数,参数是一个函数,函数中有3个参数 参数1:item必须。当前元素的值 参数2:index,可选。当前元素在数组中的索引值 参数3&#xff…