Hi,大家好!我是白日梦!

今天我要跟你分享的MySQL话题是:“了解Flush-List吗?顺便说一下脏页的落盘机制!(文末送书)”

本文是MySQL专题的第 8 篇,共110篇。

一、回顾

现在稍微回顾一下:前面几篇文章介绍了LRU List、Free List。

MySQL启动后Buffer Pool会初始化。Buffer Pool也会初始化好N多个空白的缓存页,以及它们的描述数据会被组织成LRU链表以及FreeList 双向链表。

这时你从磁盘中读取一个数据页,会先从Free List中找出一个空闲缓存页的描述信息,然后将你读出的数据页中加载进缓存页中。同时将缓存页的描述信息从Free List中剔除,此外该描述信息块还会被维护进LRU链表中。

数据页被加载进Buffer Pool后你就可以对其进行变更操作了。

二、Flush List

为了加快响应客户端的速度,MySQL会在Buffer Pool中对数据进行修改,可是一旦你对LRU链表中的缓存页做了修改,那该页中的数据和磁盘中的数据页信息就不一致了!大家一般管这种数据页叫做脏页。

为了保证数据的最终一致性,MySQL是需要将脏页刷新回磁盘的!

但是问题是:需要将哪些数据页刷新回磁盘呢?

这就引出了Flush List~

Flush List 和 Free List很像,都是由Buffer Pool中数据描述信息组织而成的双向链表。

一旦你对内存中的缓冲页作出了修改,那该缓冲页对应的描述信息块就会添加进 Flush List。这样当Buffer Pool中的数据页不够用时,我们就可以优先将 Flush List中的脏数据页刷新进磁盘中。

如果你读了前几篇文章那你肯定知道了 LRUList、FreeList、FlushList、Buffer Pool、脏页、脏数据。

下面乘胜追击!一起看一下脏页的落盘机制

三、什么是脏页?什么是脏数据?

  • 什么是脏页?

    我在介绍Flush List 的那篇文章有提及,脏页就是LRU链表中被修改了的缓存页。他们和磁盘中的数据页不一致,脏页是需要被刷新回磁盘的。

  • 什么是脏数据?

    这个问题其实引出了脏读的概念。举个例子:事物A中读取到了事物B中未提交的数据,我们管这些数据叫做脏数据。

四、脏页刷回磁盘的时机

当Buffer Pool不够用时,根据LRU机制,MySQL会将Old SubList部分的缓存页移出LRU链表。如果被移除出去的缓存页的描述信息在Flush List中,MySQL就得将其刷新回磁盘。

InnoDB存储引擎将脏页刷回磁盘的时机有蛮多的,你可以把它当作拓展知识大概浏览一下。

1、当MySQL数据库关闭时,会将所有的脏数据页刷新回磁盘。这个功能由参数:innodb_fast_shutdown=0控制,默认让InnoDB在关闭前将脏页刷回磁盘,以及清理掉undo log。

2、有一个后台线程Master Thread会按照每秒或者每十秒的速度,异步的将Buffer Pool中一定比例的页面刷新回磁盘中。

3、在MySQL5.7中,Buffer Pool的刷新由page cleaner threads完成。

  • 我们可以通过innodb_page_cleaners参数控制page cleaner threads线程的数量,但是当你将这个数值调整的比Buffer Pool的数量还大时,MySQL会自动将 innodb_page_cleaners数量设置为innodb_buffer_pool_instances的数量。
  • Innodb1.1.x之前需要保证LRU列表中有至少100个空闲页可以使用。低于这个阈值就会触发脏页的刷新。
  • 从MySQL5.6,也就是innodb1.2.X开始,innodb_lru_scan_depth参数为每个缓冲池实例指定page cleaner threads 扫描Buffer Pool来查找要刷新的脏页的下行距离。默认为1024,该后台线程每秒都会执行一次。

4、当脏数据页太多时,也会触发将脏数据页刷新回磁盘。该机制可由参数innodb_nax_dirty_pages_pct控制,比如将其设置为75,表示,当Buffer Pool中的脏数据页达到整体缓存的75%时,触发刷新的动作。现实情况是该参数默认值为0。以此来禁用Buffer Pool早期的刷新行为。

5、当redo log不可用时,也会强制脏页列表中的脏页刷新回磁盘。这个机制同样由一个后台线程完成。

六、其他关于脏页刷新的知识点

刷新临接数据页:意思是当MySQL将某脏页刷新回磁盘时,是否也以相同的态度将该脏页邻接的脏页一并刷新回磁盘。

可以通过参数innodb_flush_neighbors控制该过程。

  • 设置为0时表示,禁用刷新邻接的功能。
  • 设置为1时表示,以相同的态度刷新其邻接的脏页。
  • 设置为2时表示,以相同的程度刷新脏页。

那如何选择将其设置为哪种状态呢?

你可以根据MySQL实例所在机器的存储类型来决定。如果为HDD存储建议将其开启,因为HDD的磁盘刷新速率较低,开启该参数后可以有效的减少IO操作。相反如果使用SSD存储,其本身就有高磁盘IO的特性,建议禁用该参数。

七、推荐阅读

1、谈谈MySQL中基数是什么?

2、聊聊什么是慢查?如何监控?如何排查?

3、对Not Null字段插入Null值有啥现象?

4、能谈谈year、date、datetime、time、timestamp的区别吗?

5、你有没有搞混查询缓存和Buffer Pool?谈谈看!

6、你知道数据库缓冲池中的LRU-List吗?

7、了解InnoDB的FreeList吗?谈谈看!

参考:

https://dev.mysql.com/doc/refman/5.7/en/innodb-parameters.html

https://dev.mysql.com/doc/refman/5.7/en/innodb-buffer-pool-flushing.html

https://dev.mysql.com/doc/refman/5.7/en/innodb-parameters.html#sysvar_innodb_lru_scan_depth

《MySQL技术内幕》

关注送书!《Netty实战》

文章公号 首发!连载中!关注微信公号回复:“抽奖” 还可参加抽活动



面试题:了解MySQL的Flush-List吗?顺便说一下脏页的落盘机制!(文末送书)的更多相关文章

  1. 冰河又一MySQL力作出版(文末送书)!!

    写在前面 继<海量数据处理与大数据技术实战>之后,冰河的又一力作<MySQL技术大全:开发.优化与运维实战>出版,相信这本书对任何想系统学习MySQL的小伙伴来说,都会带来实质 ...

  2. 面试题:MySQL索引为什么用B+树?

    面试题:MySQL索引为什么用B+树? 前言 讲到索引,第一反应肯定是能提高查询效率.例如书的目录,想要查找某一章节,会先从目录中定位.如果没有目录,那么就需要将所有内容都看一遍才能找到. 索引的设计 ...

  3. python面试题七: mysql数据库

    ---------------------------------------------------------------------------------------------------- ...

  4. mysql命令flush privileges命令

    修改一个用户的密码,命令如下 mysql> update user set password=password('新密码') where user='用户名'; 执行后报错: ERROR 105 ...

  5. 细看InnoDB数据落盘 图解 MYSQL 专家hatemysql

    http://hatemysql.com/?p=503 1.  概述 前面很多大侠都分享过MySQL的InnoDB存储引擎将数据刷新的各种情况.我们这篇文章从InnoDB往下,看看数据从InnoDB的 ...

  6. MySQL:刷脏页

    1. 脏页,干净页 当内存数据页和磁盘数据页上的内容不一致时,我们称这个内存页为脏页: 内存数据写入磁盘后,内存页上的数据和磁盘页上的数据就一致了,我们称这个内存页为干净页. 2. 刷脏页的时机 2. ...

  7. __细看InnoDB数据落盘 图解 MYSQL

    http://hatemysql.com/?p=503 1.  概述 前面很多大侠都分享过MySQL的InnoDB存储引擎将数据刷新的各种情况.我们这篇文章从InnoDB往下,看看数据从InnoDB的 ...

  8. Mysql的刷脏页问题

    平时的工作中,不知道你有没有遇到过这样的场景,一条 SQL 语句,正常执行的时候特别快,但是有时也不知道怎么回事,它就会变得特别慢,并且这样的场景很难复现,它不只随机,而且持续时间还很短. 当内存数据 ...

  9. MySQL中InnoDB脏页刷新机制Checkpoint

    我们知道InnoDB采用Write Ahead Log策略来防止宕机数据丢失,即事务提交时,先写重做日志,再修改内存数据页,这样就产生了脏页.既然有重做日志保证数据持久性,查询时也可以直接从缓冲池页中 ...

随机推荐

  1. JVM系列【2】Class文件结构

    JVM系列笔记目录 虚拟机的基础概念 class文件结构 class文件加载过程 jvm内存模型 JVM常用指令 GC与调优 如何查看class字节码文件 在idea中可以通过插件BinEd来查看二进 ...

  2. BigInteger和BigDecimal

    BigInteger BigInteger的作用是对整数做计算,一般的使用String类型初始化BigInteger,它除了封装了基本的加减乘除运算外还提供了signum(),abs()等函数,使用方 ...

  3. 例题4-2 刽子手游戏(Hangman Judge, UVa 489)

    #include<stdio.h> #include<string.h> int ok ,no; int left ,chance; char s[20] ,s2[20]; v ...

  4. Windows环境下vscode Live Server插件如何开启https

    0x01 vscode http插件 Live Server如何开启https 在本机端的开发环境下,如果要测试一些需要HTTPS的功能可以使用mkcert给自己颁发凭证 0x02 安装步骤如下: 1 ...

  5. Docker结合.Net Core初步使用

    Docker是一项比较流行的容器化技术,可以让开发者将应用以及应用依赖的环境,依赖包一起打包到容器中,然后部署容器到生产环境就可以了,解决了应用程序部署到不同服务器环境带来的问题(很多开发人员都遇到过 ...

  6. ServletRequest使用介绍

    ServletRequest: 定义将客户端请求信息提供给某个 servlet 的对象:servlet 容器创建 ServletRequest 对象,并将该对象作为参数传递给该servlet的serv ...

  7. 简单又强大的pandas爬虫 利用pandas库的read_html()方法爬取网页表格型数据

    文章目录 一.简介 二.原理 三.爬取实战 实例1 实例2 一.简介 一般的爬虫套路无非是发送请求.获取响应.解析网页.提取数据.保存数据等步骤.构造请求主要用到requests库,定位提取数据用的比 ...

  8. 闭包 - Js函数笔记

    闭包 当函数被保存到外部时,将会生成闭包 闭包会导致原有作用域链不释放,造成内存泄漏 类似的代码就叫闭包 闭包的运行作用域 代码 a被执行,b被定义并保存出来 a结束,b被执行时,a的执行期上下文指向 ...

  9. Mysql JDBC-mysql-Driver queryTimeout分析

    Mysql jdbc的queryTimeout分析 Mysql的jdbc-driver com.mysql.jdbc.Driver 设置queryTimeout方法 com.mysql.jdbc.St ...

  10. AWS Lambda 借助 Serverless Framework,迅速起飞

    前言 微服务架构有别于传统的单体式应用方案,我们可将单体应用拆分成多个核心功能.每个功能都被称为一项服务,可以单独构建和部署,这意味着各项服务在工作时不会互相影响 这种设计理念被进一步应用,就变成了无 ...