预读失效
预读失效
上面我们提到了缓冲池的预读机制可能会预先加载相邻的数据页。假如加载了 20、21 相邻的两个数据页,如果只有页号为 20 的缓存页被访问了,而另一个缓存页却没有被访问。此时两个缓存页都在链表的头部,但是为了加载这两个缓存页却淘汰了末尾的缓存页,而被淘汰的缓存页却是经常被访问的。这种情况就是预读失效,被预先加载进缓冲池的页,并没有被访问到,这种情况是不是很不合理。
————————————————
- 让预读加载进缓存且尚未被访问的页,停留在缓冲池LRU里的时间尽可能短;
- 让真正被读取的页,才挪到缓冲池LRU的头部;
缓冲池污染
还有一种情况是当执行一条 SQL 语句时,如果扫描了大量数据或是进行了全表扫描,此时缓冲池中就会加载大量的数据页,从而将缓冲池中已存在的所有页替换出去,这种情况同样是不合理的。这就是缓冲池污染,并且还会导致 MySQL 性能急剧下降。
例如,有一个数据量较大的用户表,当执行:
select * from user where name like "%John%";
虽然结果集可能只有少量数据,但这类like不能命中索引,必须全表扫描,就需要访问大量的页。
————————————————