mysql内存结构介绍(一)

mysql内部结构

在这里插入图片描述

1

Server层
主要包括连接器、查询缓存、分析器、优化器、执行器等,涵盖MySQL的大多数核心服务功能,以及所有的内置函数(如日期、时间、数学和加密函数等),所有跨存储引擎的功能都在这一层实现,比如存储过程、触发器、视图等。
Store层
存储引擎层负责数据的存储和提取。其架构模式是插件式的,支持InnoDB、
MyISAM、Memory等多个存储引擎。

2 Service层结构

2.1
连接器:我们知道由于MySQL是开源的,他有非常多种类的客户navicat,mysql,front,jdbc,SQLyog等非常丰富的客户端,这些客户端要向mysql发起通信都必须先跟Server端建立通信连接,而建立连接的工作就是有连接器完成的。
第一步,
你会先连接到这个数据库上,这时候接待你的就是连接器。连接器负责跟客户端建立连接、获取权限、维持和管理连接。
连接完成后,如果你没有后续的动作,这个连接就处于空闲状态,你可以在
show processlist命令中看到它。如果sleep代表空闲状态。这里就不贴图啦。
客户端如果长时间不连接,那么就会自动断开,连接等待时长默认8小时。

可以通过show global VARIABLES like '%wait_timeout%'; 进行查看

2.2
查询缓存:连接建立完成后,你就可以执行select语句了。执行逻辑就会来到第二步:查询缓存。
一般建议大家在静态表里使用查询缓存,什么叫静态表呢?就是一般我们极少更新的表。比如,一个系统配置表、字典表,那这张表上的查询才适使用查询缓存。好在MySQL也提供了这种“按需使用”的方式。
你可以将my.cnf参数query_cache_type设置成DEMAND。
query_cache_type = 0 off 1 on 2 DEMAND。
按需使用select SQL_CACHE * from dict;

show global variables like "%query_cache_type%";查看是否开启缓存
show status like'%Qcache%';查看缓存命中率以下介绍各参数含义:
Qcache_free_blocks:表示查询缓存中目前还有多少剩余的blocks,如果该值显示较大,
则说明查询缓存中的内存碎片过多了,可能在一定的时间进行整理。
Qcache_free_memory:查询缓存的内存大小,通过这个参数可以很清晰的知道当前系统的查询内存是否够用,是多了,还是不够用,DBA可以根据实际情况做出调整。
Qcache_hits:表示有多少次命中缓存。我们主要可以通过该值来验证我们的查询缓存的效果。数字越大,缓存效果越理想。
Qcache_inserts:表示多少次未命中然后插入,意思是新来的SQL请求在缓存中未找到,不得不执行查询处理,执行查询处理后把结果insert到查询缓存中。这样的情况的次数,次数越多,表示查询缓存应用到的比较少,效果也就不理想。当然系统刚启动后,查询缓存是空的,这很正常。
Qcache_lowmem_prunes:该参数记录有多少条查询因为内存不足而被移除出查询缓存。
通过这个值,用户可以适当的调整缓存大小。
Qcache_not_cached:表示因为query_cache_type的设置而没有被缓存的查询数量。
Qcache_queries_in_cache:当前缓存中缓存的查询数量。
Qcache_total_blocks:当前缓存的block数量。

2.3分析器:
如果没有命中查询缓存,就要开始真正执行语句了。首先,MySQL需要知道你要做什么,因此需要对SQL语句做解析。分析器先会做“词法分析”。
2.4优化器:
经过了分析器,MySQL就知道你要做什么了。在开始执行之前,还要先经过优化器的处理。优化器是在表里面有多个索引的时候,决定使用哪个索引;或者在一个语句有多表关联(join)的时候,决定各个表的连接顺序。
2.5执行器:
执行器就会根据表的引擎定义,去使用这个引擎提供的接口
以上对Service层的各个组件就有了一个简单地介绍

3.Store层结构

这里只介绍我们常用的InnoDB
在这里插入图片描述

Service层执行器调用存储层接口一共经理以上8步。这里我们一一介绍:
1.首先我们会将磁盘文件idb文件中查找到所需数据页Page。一页是16k大小,按页缓存到Buffer Pool中。(注意:Buffer Pool有大小设置,内部实现了LRU淘汰策略,后续会将到如何避免buffer污染)
2.将数据库旧值写入undo日志(mvcc机制会用到undo日志链)
3.更新buffer pool,首先更新buffer pool,并没有直接更新磁盘文件。
4.写redo log buffer。
5.准备提交事务时写入redo日志文件
6.归档文件binlog写入,属于Service层
7.确认提交时,binog日志需要把commit标记写入redo日志,保证数据一致性。
8.Buffer pool IO线程随机写入idb文件。

为什么Mysql不能直接更新磁盘上的数据而且设置这么一套复杂的机制来执行SQL了?
因为来一个请求就直接对磁盘文件进行随机读写,然后更新磁盘文件里的数据性能可能相当差。因为磁盘随机读写的性能是非常差的,所以直接更新磁盘文件是不能让数据库抗住很高并发的。Mysql这套机制看起来复杂,但它以保证每个更新请求都是更新内存BufferPool,然后顺序写日志文件,同时还能保证各种异常情况下的数据一致性。更新内存的性能是极高的,
然后顺序写磁盘上的日志文件的性能也是非常高的,要远高于随机读写磁盘文件。

文件作用:
undo日志: InnoDB独有,用户数据回滚,以及保证mvcc机制。顺序写
redo日志:InnoDB独有,用于还原Buffer pool缓存。顺序写
binlog日志:Service层,用于归档,以及主从机制数据同步。

mvcc机制实现原理这里只介绍可重复度实现机制这个隔离性就是靠MVCC(Multi-Version

在串行化隔离级别为了保证较高的隔离性是通过将所有操
作加锁互斥来实现的。Mysql在读已提交和可重复读隔离级别下都实现了MVCC机制。原理是通过undo日志版本链与read view机制详解。
undo日志链:
在这里插入图片描述

根据上面内容我们的值,innodb会维护undo日志链。并通过指针指向上一个版本。
readview机制,当事务开启,执行任何查询sql时会生成当前事务的一致性视图read-view,该视图在事务结束
之前都不会变化(如果是读已提交隔离级别在每次执行查询sql时都会重新生成),这个视图由执行查询时所有未提交事
务id数组(数组里最小的id为min_id)和已创建的最大事务id(max_id)组成,事务里的任何sql查询结果需要从对应版本链里的最新数据开始逐条跟read-view做比对从而得到最终的快照结果。
版本链比对规则:
1.如果row的trx_id落在绿色部分(trx_id<min_id),表示这个版本是已提交的事务生成的,这个数据是可见的;
2.如果row的trx_id落在红色部分(trx_id>max_id),表示这个版本是由将来启动的事务生成的,是不可见的(若row的trx_id就是当前自己的事务是可见的);
3.如果row的trx_id落在黄色部分(min_id<=trx_id<=max_id),那就包括两种情况a.若row的trx_id在视图数组中,表示这个版本是由还没提交的事务生成的,不可见(若row的trx_id就是当前自己的事务是可见的);b.若row的trx_id
不在视图数组中,表示这个版本是已经提交了的事务生成的,可见。

以上就是mvcc机制对比规则。

今天的内容就介绍到这里,后续为大家介绍b+树,以及如何优化索引,如果为一个复杂查询建立一个高效的三星索引。(感谢hqp)

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值