、merge的触发机制
当需要更新一个数据页时,如果数据页在内存中就直接更新,而如果这个数据页还没有在内存中的话,在不影响数据一致性的前提下,InnoDB 会将这些更新操作缓存在 change buffer 中,这样就不需要从磁盘中读入这个数据页了。在下次查询需要访问这个数据页的时候,将数据页读入内存,然后执行 change buffer 中与这个页有关的操作。change buffer 用的是 buffer pool 里的内存。唯一索引要判断唯一性,需要读取数据进内存,所以用不到change buffer。将数据从磁盘读入内存涉及随机 IO 的访问,是数据库里面成本最高的操作之一。普通索引使用change buffer 因为减少了随机磁盘访问,所以对更新性能的提升是会很明显的。将 change buffer 中的操作应用到原数据页,得到最新结果的过程称为 merge。除了访问这个数据页会触发 merge 外,系统有后台线程会定期 merge。在数据库正常关闭(shutdown)的过程中,也会执行 merge 操作。所以读多写少的数据用change buffer会频繁触发 merge 过程。起了副作用。
redo log 主要节省的是随机写磁盘的 IO 消耗(转成顺序写),而 change buffer 主要节省的则是随机读磁盘的 IO 消耗
merge 的执行流程是这样的:
1. 从磁盘读入数据页到内存(老版本的数据页);
2. 从 change buffer 里找出这个数据页的 change buffer 记录 ( 可能有多个),依次应用,得到新
版数据页;
3. 写 redo log 这个 redo log 包含了数据的变更和 change buffer 的变更。
到这里 merge 过程就结束了。这时候,数据页和内存中 change buffer 对应的磁盘位置都还没有修
改,属于脏页,之后各自刷回自己的物理数据,就是另外一个过程了(各自刷回自己的物理数据这个应该就是刷脏页,术语为flush操作,也就是redo log日志落盘到实际磁盘上的操作)
再加一个 博客链接 https://juejin.im/post/6892914758006079496#heading-3