当前位置: 首页 > news >正文

mysql进阶(五)

1 Null列表有啥作⽤?列表中的值是什么?

        头信息区再向右就是NULL值列表的可变区域,⽤来存储数据⾏中所有列允许为Null的值从⽽节省 空间,具体的实现⽅式是,⽤1BIT的⼤⼩来表⽰⾏中某⼀列是否为空,这样空列就不需要记录在真 实数据区域中了。

        为每个没有定义 NOT NULL 约束也就是可以为NULL的列在NULL值列表中都安排了⼀个bit位,按 列序号从⼩到⼤的顺序从右⾄左依序安排,这就是常说的逆序排列,NULL值列表最⼩1字节即 8bit,如果没有那么多可以为NULL的列,则会⽤0补满8bit,如果为值为NULL的列超过8个,则新 开辟1字节的空间,依此类推;

         • 如果某列为空,则NULL值列表中对应的bit设置为1,这样只⽤了⼀bit就存储了NULL列,⾮常节省空间 。

只有某行的数据为null,在null值列表里面采用1来表示。

2. 变⻓字段列表有啥作⽤?列表中的值是什么?

        查看编码集所占的字节数:show charset;

        • ⾏结构的最左侧是变⻓字段列表,也叫可变字段⻓度列表,在这个列表中记录了数据⾏中所有变⻓ 字段的实际⻓度,这样做的⽬的,是为了在真实数据区域,可以根据列的⻓度进⾏列与列之间的分 割;

        • 需要记录的变⻓字段类型常⻅的有varchar、varbinary、text、blob,以及当使⽤了例如utf-8、 gbk等变⻓字符集的char类型,当char类型的字节数可能超过768个字节时,⽐如使⽤utf8mb4字符集时定义了char(255),这个字段的最⼤字节数是4*255=1020

         • 每个变⻓字段分配1~2个字节来存放这些字段的真实⼤⼩,放置顺序也是按表中字段的顺序从右⾄ 左逆序排列;

        • 2个字节最⼤可以表⽰65535个字节数,按照最⼤⻓度字符串,⽐如utf8mb4,⼀个字符占⽤最多4个 字节计算,2个字节最多可以表⽰65535/4=16383个字符,列数据类型varchar的⻓度上限16383就 是根据这个计算来的;

         • 需要特别说明的是,如果text、blob存储的内容过⼤,⼀个⻚已经不够放了,就会把这个列放⼊⼀ 个叫"溢出⻚"的独⽴空间中,在这个数据⾏对应的真实数据处,只使⽤20个字节来标记这个溢出⻚的位置信息。

        如何记录变⻓字段的实际⻓度?

        读取⻓度时如何处理粘包问题?

3. 其他的⾏格式与DYNAMIC有什么区别?

        REDUNDANT冗余格式 ,已被淘汰,之所以存在是为了与旧版本MySQL兼容,不建议使⽤,。

         COMPRESSED压缩格式 ,⾏结构与 DYNAMIC 完全相同,只是会对数据进⾏压缩,以减少对空间的占⽤。

         COMPACT紧凑格式 ,在结构上与 DYNAMIC 相同,只是对超⻓字段的处理上有些区别,它不会把所有超⻓数据都放在溢出 ⻚中,⽽是会在本⾏中保留前768个字节的数据,多出的部分放在溢出⻚中,溢出⻚的地址额外⽤20个 字节表⽰,那么在本⾏的列中就会占⽤768+20个字节。

4. InnoDB内存结构 

的InnoDB架构图如下所示:

        InnoDB存储引擎中内存结构主要分为:Buffer Pool 缓冲池、Change Buffer变更缓冲区、adaptive_hash_index ⾃适应哈希索引 、L og Buffer ⽇志缓冲区。

        为什么需要内存结构?

        从MySQL实现的⻆度来思考这个问题,数据库的作⽤就是保存数据,⽤⼾的真实数据最终都会保存 在磁盘上,在查询数据的过程中,如果每次都从磁盘上读取会严重影响效率,为了提⾼数据的访问 效率,InnoDB会把查询到的数据缓存到内存中,当再次查询时,如果⽬标数据已经存在于内存 中,就可以从内存中直接读取,从⽽⼤幅提升效率。

         也就是说磁盘结构中的⽂件是⽤来保存数据实现数据持久化的,内存结构是⽤来缓存数据提升效率的。

5. 缓冲池-BufferPool

        缓冲池主要⽤来缓存被访问的InnoDB表和索引数据⻚,是主内存中的⼀⽚区域,允许直接从内存 访问频繁使⽤的数据从⽽提⾼效率。在专⽤数据库服务器上,通常会将多达80%的物理内存分配给缓冲池。

         其次缓冲池不仅缓存了磁盘的数据⻚,也存储了锁信息、ChangeBuffer信息、Adaptivehash index、Doublewrite buffer等信息。

        1、缓冲池是如何组织数据的?

        首先,每个InnoDB表空间在磁盘上对应⼀个 .ibd ⽂件,其中包含了叶⼦节点段和⾮叶⼦节点段等逻辑 段,段中包含了区组,区组中管理着区,区别包含数据⻚,数据⻚中包含数据⾏,每分别对着不同 的数据结构⽬的就是便于数据的管理与⾼效访问

        2、缓冲池的结构、

我们知道磁盘中的数据⻚⼤⼩默认是16KB,并且通过头信息中的 next_record 记录下⼀⾏地址偏移量。

        缓冲池中⻚与⻚之间是如何建⽴连接的? 

 

        缓冲池中主要缓存的是磁盘中的数据⻚,由于数据⻚中没有⼀个字段⽤来表⽰内存中下⼀⻚的地 址,InnoDB定义了"控制块"的数据结构,控制块中有⼀个指向数据⻚内存地址的指针,实现"控制 块"与数据⻚的⼀⼀对应,并且把每个控制块连接成⼀个双向链表,⽤⼀个单独的头节点记录链表 的第⼀个和最后⼀个节点,这样通过遍历控制块链表就可以遍历内存中的数据⻚。

         内存中的数据⻚与磁盘上的数据⻚是什么关系?

        磁盘上的数据⻚加载到内存中后,在缓冲池中都有⼀个内存⻚与它对应,只不过内存中管理的是控制 块组成的链表,控制块有⼀个指针指向了内存中真实的数据⻚

 

下图是以instance为单位对缓冲池进行空间扩展时:

 注意:启动调整⼤⼩操作时,在所有活动事务完成后操作才会开始。⼀旦调整⼤⼩操作开始,新的 事务和操作必须等到调整⼤⼩操作完成才可以访问缓冲池。

 6. 控制块与Page是如何初始化的?

        前⾯介绍了 Chunk 中管理的是具体的数据⻚,当缓冲池初始化完成时会把每个数据⻚所占⽤的内 存空间和对应的控制块分配好,只不是没有从磁盘加载数据时,内存中的数据⻚是空的⽽已。

        • 当缓冲池初始化的过程中,会为 Chunk 分配置内存空间,此时"控制块"会从 从左向右进⾏初始化,数据⻚所占的内存会从 Chunk 的内存空间 Chunk 的内存空间从右向左进⾏初始化,当所剩的 内存空间不够⼀组"控制块"+数据⻚所占的空间时,就会产⽣碎⽚空间,如果适好够⽤则不会出现 碎⽚空间,如下图所⽰:

        内存初始化完成之后,建⽴控制块与内存中缓冲数据⻚之间的关系,从左开始第⼀个控制块指向第⼀个缓冲数据⻚的内存地址 

        可以通过缓冲池配置来提升性能,通过配置以下关于缓冲池的系统变量来提⾼性能:

         • 配置缓冲池⼤⼩

        • 配置多个缓冲池实例

        • 防⽌缓冲池扫描

        • 配置缓冲池预取(预读)

         • 配置缓冲池刷新策略

        • 保存和恢复缓冲池状态

         • 从核⼼⽂件中排除缓冲池⻚

        • 这些变量可以通过以下语句查看:SHOW VARIABLES LIKE 'innodb_buffer_pool%';

7. 缓冲池中的⻚是如何进⾏管理的?

        其实管理的是内存中数据页的状态。

answer:

       内存中有这么多数据⻚如何快速找到⽬标⻚?

         • ⾸先第⼀种办法是通过遍历,这种做法显⽰不能满⾜性能要求

        • InnoDB采⽤的是 Page Hash (b+树)的⽅式,也就是每当把磁盘中数据⻚加载到内存时,⽤数据⻚的表 空间Id和⻚号做为Key,当前⻚在内存中的地址做为Value保存起来,每次查询时就可以通过Key快 速定位到⽬标⻚,如果内存中没有⽬标⻚,则从磁盘中获取。

         缓冲池中的数据放不下了怎么办?

        • InnoDB根据根据⾃⾝的实际场景,使⽤淘汰策略来淘汰相应的数据⻚,从⽽释放出内存空间,以 便新的数据⻚加载到内存中。

8. 缓冲池采⽤哪种淘汰策略?是如何实现的?

        怎么查看当前缓冲池的信息:

        通过使⽤ SHOW ENGINE InnoDB STATUS 访问 InnoDB 标准监视器输出中 BUFFER POOL AND MEMORY 部分查看有关缓冲池的指标。缓冲池指标位于InnoDB标准监视器输出的缓冲池和内 存部分:

9. 变更缓冲区-ChangeBuffer

        作用:提高修改数据时的作用。

        change buffer管理的是change buffer页。

简洁修改如下:

 当永远没有事务二发生时,我们只能进行两次io操作,即先读后写。

        answer:

        • 变更缓冲区⽤来缓存对⼆级索引数据的修改,当数据⻚没有被回载到内存中时先把修改缓存起来, 等到其他查询操作发⽣时数据⻚被加载到内存后,再直接修改内存中的数据⻚,从⽽达到减少磁盘 I/O的⽬的。

        为什么是⼆级索引?

         • 关于索引在数据库初阶已经做了介绍,我们知道索引分为聚集索引(主键)和⼆级索引(⾃定义)

        • 由于聚集索引具有唯⼀性,我们分析⼀下聚集索引为什么不能被放⼊变更缓存,假设表中有⼀个主 键( ID ),现在有两条 INSER 语句,都在插⼊数据时ID的值相同 (id=1) ,那么在变更缓冲区中 就存在两个修改操作,如果以后要合并到缓冲池中,这时就会出现重复的主键值,所以聚集索引的 修改不能被加⼊到变更缓冲区;

         • 与聚集索引不同,⼆级索引通常是不唯⼀的,并且向⼆级索引中插⼊数据时由于数据列不同,所以 位置相对随机,同样对于删除和更新操作可能会影响不相邻的⼆级索引⻚,如果每次都从磁盘读取 数据就会发⽣⼤量的随机I/O,以变更缓冲区的⽅式先将修改缓存起来,当真正的读取数据时再把 修改合并到缓冲池中可以提升效率。

10. 变更缓冲区的主要配置项都有哪些?

        主要的配置项有缓冲类型和更改缓冲区的最⼤⼤⼩:

1. 缓冲类型

        在修改⼆级索引数据时变更缓冲区可以减少磁盘I/O从⽽提⾼效率,但是变更缓冲区占⽤了缓冲池 的⼀部分空间,从⽽减少了可⽤于缓存数据⻚的内存,如果业务场景读多写少,或者表中的⼆级索引 相对较少,那么可以考虑禁⽤更改缓冲从⽽提⾼缓冲池空间。

        可以通过选项⽂件或 SET GLOBAL 语句对系统变量 innodb_change_buffering 进⾏设 置,来控制变更缓冲区对于插⼊、删除操作(索引记录被标记为删除)和清除操作(当索引记录被物理删 除时)的开启或禁⽤:

        删除操作:索引记录被标记为删除

        清除操作:索引记录被物理删除时

        更新操作:是插⼊和删除操作的组合

2. 更改缓冲区的最⼤⼤⼩

        通过 innodb_change_buffer_max_size 系统变量可以设置更改缓冲区的最⼤⼤⼩,默认为 25,最⼤为50,表⽰更改缓冲区占缓冲池内存总⼤⼩的百分⽐。

         • 在有⼤量插⼊、更新和删除的业务场景中,可以考虑增加 innodb_change_buffer_max_size 的值,在⼤部分是读多写少,⽐如⽤于报表的静态数据 场景中考虑减⼩ innodb_change_buffer_max_size 的值

        • 需要注意的是,如果更改缓冲区占了缓冲池太多的内存空间,会导致缓冲池中的数据⻚更快地淘 汰。

        怎么查看当前变更缓冲区的信息

通过使⽤ SHOW ENGINE InnoDB STATUS 访问 InnoDB 标准监视器输出中 INSERT BUFFER AND ADAPTIVE HASH INDEX 部分查看有关更改缓冲区状态的信息,如下所示:

11. ⾃适应哈希索引

        ⾃适应哈希索引的主要作⽤就是提升查询效率

b+树数据存储分布:

12 ⽇志缓冲区

        ⽇志缓冲区的作⽤?

        ⽇志缓冲区是服务器启动时向操作系统申请的⼀⽚连续的内存区域,存储即将要写⼊磁盘⽇志⽂件 的数据。

         • 在对数据库进⾏DML操作时,InnoDB会记录对应操作的⽇志,⽐如为保证数据完整性实现数据库崩溃恢复的RedoLog,这些⽇志会⾸先写⼊LogBuffer中,从⽽解决同步写磁盘导致的性能问题, 然后根据不同落盘策略最终写⼊磁盘。

        如果⽇志不通过LogBuffer直接写⼊磁盘,那么每次进⾏DML操作都会进⾏⼀次磁盘I/O,这样会严 重影响效率,所以把⽇志统⼀写⼊内存中的LogBuffer,根据刷盘策略统⼀进⾏落盘(一次写多少,写多少次会罗盘)操作,可以实 现⼀次磁盘I/O写⼊多条⽇志,从⽽提升效率

13 InnoDB磁盘⽂件

        InnoDB的磁盘⽂件主要是表空间⽂件和其他⽂件,表空间包括:系统表空间、独⽴表空间、通⽤ 表空间、临时表空间和撤销表空间(undo tablespace);其他⽂件有重做⽇志和双写缓冲区

        表空间可以理解为MYSQL为了管理数据⽽设计的⼀种数据结构,主要描述的对结构的定义,表空间⽂件是对定义的具体实现,以⽂件的形式存在于磁盘上,一般说的表空间指的就是表空间⽂件。

14 系统表空间

        系统表空间的作⽤:

        • 系统表空间存储了MySQL中所有系统表的数据,也包括数据字典;

        • 系统表空间也是变更缓冲区的存储区域,当数据库服务器关闭时,没有合并到缓冲池的⼆级索引修 改操作被保存到系统表空间;

         • 在以前的版本中,系统表空间也包含双写缓冲区,从MySQL8.0.20开始,双写缓冲区从系统表空间 中移到单独的⽂件中。

        系统表空间⽂件保存在哪⾥:

         • 系统表空间可以对应⼀个或多个数据⽂件,默认情况下,MySQL在 空间数据⽂件 data ⽬录中创建⼀个系统表 ibdata1 。系统表空间数据⽂件的⼤⼩和数量由 innodb_data_file_path 启 动选项定义

15 系统表空间配置的选项

        可以通过 innodb_data_file_path 选项定义,如果没有指定 innodb_data_file_path 的值,则默认创建⼀个⼤⼩可以⾃动扩展的数据⽂件,⽂件名为 ibdata1 ,初始⼤⼩ 12MB 。

 

        根据实际应⽤场景通过配置对应的系统变量来指定数据⽂件的⼤⼩、名称、数量和其他属性 。在修改系统表空间配置时,先停⽌MySQL服务,修改完成后,再重新启动MySQL服务之后⽣效。

16 独⽴表空间-File-Per-TableTablespace

        File-Per-Table 表空间包含单个InnoDB表的数据和索引,默认情况下每张表都对应⼀个表空 间数据⽂件,便于维护,所以称为 File-Per-Table Tablespace。

        独立表空间文件创建在相对应数据库,var/lib/mysql/数据库/xxx.idb;

        每个表都对应⼀个独⽴表空间吗:

        独⽴表空间的优点和缺点

 

17 撤销表空间-UndoTablespaces

        撤销表空间的作⽤:撤销表空间中包含撤销⽇志(UndoLog),撤销⽇志记录了如何撤销事务对聚集索引记录的最新更改 (事务的回滚),通过对事务的回滚,从⽽保证事务ACID特性中的原⼦性。

        要查看撤销表空间名称和路径,请查询 INFORMATION_SCHEMA.FILES:

        可以⼿动创建撤销表空间吗,通过使⽤  语法 CREATE UNDO TABLESPACE 语句可以创建撤销表空间

        CREATE UNDO TABLESPACE tablespace_name  ADD DATAFILE 'file_name.ibu';

18 删除撤销表空间

删除撤销表空间的步骤:

        查看撤销表空间的状态:

 

根据上图可以明了的查看系统撤销表空间和用户自定义的撤销表空间。

19 撤销⽇志-UndoLog

        当事务对数据进⾏修改的时候,每个修改操作都会在磁盘上创建与之对应的UndoLog,当事务需 要回滚时,会根据UndoLog逐⼀进⾏撤销操作,从⽽保证事务的原⼦性。也就是说撤销⽇志是为 事务的回滚操作⽽诞⽣的机制,它是⼀个撤销操作记录的集合。

         • Undo⽇志保存在Undo⽇志段中,Undo⽇志段位于回滚段中,回滚段位于undo表空间和全局临时表空间中。

        撤销⽇志的写⼊时机:

        在事务执⾏每个DML之前,会根据DML构建对应的撤销⽇志,并申请⼀个 undo log segments (撤销⽇志段),把⽇志记录在申请到的撤销段中,再执⾏真正的DML操作,执⾏过程如 下所⽰:

ps:仅用于自己复习时做的笔记整理。

相关文章:

  • Windows控制台函数:控制台读取输入函数ReadConsoleA()
  • STM32中输入/输出有无默认电平
  • C++的内存管理
  • 单片机项目复刻需要的准备工作
  • SpringBoot参数校验:@Valid 与 @Validated 详解
  • nginx反向代理功能
  • LeetCode1871 跳跃游戏VII
  • 江协科技/江科大-51单片机入门教程——P[5-1] 模块化编程 P[5-2] LCD1602调试工具
  • 用Python写一个算24点的小程序
  • 在【k8s】中部署Jenkins的实践指南
  • CTFHub-FastCGI协议/Redis协议
  • 最新版本WebContext构造函数-避坑
  • 推理大模型的后训练增强技术-强化学习篇
  • LeetCode 哈希章节
  • Unity入门学习笔记(Day01)
  • JWT的学习
  • 探索大数据分析的无限可能:R语言的应用与实践
  • 远程登录客户端软件 CTerm 发布了 v4.0.0
  • PySide(PyQT)的contains() 方法
  • javascrip网页设计案例,SuperSlide+bootstrap+html经典组合
  • 美国调整对华加征关税
  • 秘鲁总理辞职
  • 比特币挖矿公司GRYP股价涨超171%:将与特朗普儿子创设的公司合并
  • 茅台回应“茅台1935脱离千元价位带竞争”:愿与兄弟酒企共同培育理性消费生态
  • 上海浦东机场1号、2号航站楼均推出国内出发安检24小时服务
  • 著名文物鉴赏家吴荣光逝世,享年78岁