目录
数据字典
DDL的改进-快速增加新列
实现原理
8.0.11 add column不支持的特性
测试一下性能
日志
redo
undo
索引
mutex
auto_increment
行锁增加SKIP LOCKED 和 NOWAIT 特性
事务 CATS 特性
智能选项innodb_dedicated_server
数据字典
MySQL 8.0 数据字典全部采用 INNODB 存储引擎存储,支持DDL原子性、crash safe,matadata管理也更完善了。
内部的变化如图:
MySQL 8.0 之前的Data Dictionary
MySQL 8.0
通过一图可以很清楚的看到因历史遗留问题而留下来的两套数据字典:
(1)innodb的数据字典在information_schema 里面
(2)mysql server 的数据字典存放在.frm 文件里
1.两套数据字典可能造成的情况:
比如说创建一个表,在server层的.frm文件里已经写入,但是在innodb(存储引擎)层还没来得及写入,那么等数据库恢复之后,就会发现在库里没有这个表,并且再去创建这个表的时候显示报错:这个表已存在。
2.那为了优化Data Dictionary,Innodb开发团队将server层和innodb层的数据字典合并到了innodb事务引擎中,取缔了server层的.frm文件
3. information_schema查询的时候之前是对 file 和 table 进行扫描,8.0之后可以通过view的方式展现出来,极大的提高了查询的性能。
DDL的改进-快速增加新列
此项特性是由 腾讯互娱DBA团队贡献 ,此项特性非常强大,非常感谢他们哈。
实现原理
ONline DDL 除了inplace和copy之外新加了 instant:过程不加表锁,能极大的提高执行能力和并发能力。
instant:并没有对表做大的操作,只是将变更记录到数据字典里。只是分为了两种格式:new,old。
1.add column 操作之前的数据依旧保存在老格式里;之后的数据保存的新格式里。
2. 第一次做ddl操作,会 instant flag 里记录下 “字段数量”,和新增的column的字段值。
8.0.11 add column不支持的特性
不支持将列加到中间,只支持将列加到最后。
不支持compress格式的表
如果在add column之前有fulltext,那么也不支持instant addcolumn
在数据字典表空间里的表也不支持instant add column
临时表也不支持instant add column
测试一下性能
(由于懒得写脚本,随便插了5行数据,主要是查看rows affected,所以数据少点也无所谓了)
由图三可以看出instant 的性能非常之好,也并没有全表扫描。
图三
日志
redo
并行 redo log ,并提升了 redo log 的I/O性能。
下图可以很直观的看出redo的变化。除了并行之外,还增加了1个线程 Log Flusher。
undo
可以动态的增加 undo file的个数。
redo 、undo log file 可以进行encrypt,提高了安全性
--innodb-redo-log-encrypt :=bool
--innodb-undo-log-encrypt :=bool
索引
1.倒序索引
倒序索引如果应用在主键或是2级索引,那么它的change buffer是不能使用的。并且优化器优先使用主键或二级索引。
MySQL 8.0对于group by操作不再进行隐式排序。
2.隐藏索引
优化器可以忽略隐藏索引使该索引不生效,但隐藏索引是被正常维护的,作用是用来测试无效索引,删除某索引之前,可以先设置为隐藏索引,确定对系统没有影响后再删除,以防删掉后再次重建。
mutex
消除了 buffer pool mutex,感谢percona的贡献。
auto_increment
自增ID持久化,举个例子:
1.事务1 往表中插入100行数据后提交,此时自增ID为100;事务2删除了表中10条数据后提交,此时表中还有90行数据。
2.开启事务3,插入10行数据。此时事务3的自增ID是从多少开始的呢?
8.0 版本之前是从ID为91开始的,而8.0之后呢则是从101 开始。这就是所谓的自增ID持久化。
行锁增加SKIP LOCKED 和 NOWAIT 特性
select 。。。 update no wait;select 。。。 update skip locked;
no wait :不等待持有锁的事务释放锁,直接获取锁。
skip locked:跨过已经被锁住的行。结果集可能会变少。
事务 CATS 特性
此特性是由Michigan 大学贡献。(个人感觉这个特性还挺有意思的)
拽官方名字很容易把人绕进去,那我就白话说了。首先举个例子:
事务1持有某行锁,事务2和事务3都在等待事务1释放锁从而去持有该行锁(事务2在事务3前面);而等待事务3持有锁的事务超过32个,那么等事务1释放锁之后,事务3会优先去持有该锁。
为什么是32个呢?因为这是innodb开发团队测试出来的性能比较好的临界点。并且这个32是没法自己改的。是不是很尴尬。。。
智能选项innodb_dedicated_server
此选项的意思是,它可以去主动指定你的innodb_buffer_pool等主要buffer参数的大小。具体的请自行观看官方文档。我就不在这啰嗦了。