Mysql必读MySQL 5.7 InnoDB对COUNT(*)的优化
发布时间:2020-12-12 00:49:19 所属栏目:MySql教程 来源:网络整理
导读:《Mysql必读MySQL 5.7 InnoDB对COUNT(*)的优化》要点: 本文介绍了Mysql必读MySQL 5.7 InnoDB对COUNT(*)的优化,希望对您有用。如果有疑问,可以联系我们。 导读:饱受诟病的InnoDB表COUNT(*)性能问题在5.7下做了优化,果真如此吗?1、经典需求:InnoDB表COUNT
《Mysql必读MySQL 5.7 InnoDB对COUNT(*)的优化》要点: 1、经典需求:InnoDB表COUNT(*) InnoDB引擎表经常被抱怨执行COUNT(*)的效率太差,因此此类需求通常会被建议用其他方法来满足,比如另外加一个计数器表,或者用SHOW TABLE STATUS查看大概数量. 不过,从MySQL 5.7.2起,这个问题得到了解决,我们来看看. 2、MySQL 5.7版本InnoDB对COUNT(*)的优化 MySQL每发布一个新版本,都会放出相应的Release Notes,我们注意到5.7.2版本的发布说明中提到:
简单地说就是:COUNT(*)会选择聚集索引,进行一次内部handler函数调用,即可快速获得该表总数.我们可以通过执行计划看到这个变化,例如: 很明显,在查询优化器阶段就已经得到优化了,相比效率应该杠杠的吧,我们稍后再来对比看看. 补充说下,5.7以前的版本中,COUNT(*)请求通常是:扫描普通索引来获得这个总数.也来看看5.6下的执行计划是怎样的: 可以看到,可以利用覆盖索引来完成COUNT(*)请求.MYSQL学习 3、对比测试 先看一组测试数据: 可以看到,两次数据量相当,但SQL耗时5.7约只有5.6的1/5,这个效率还是不错的吧. 我们来看看5.6和5.7版本下的status和profiling对比情况: 4、别高兴得太早 看完上面的对比测试,相信您已经心动了吧,但还别高兴得太早哦,官方文档里其实埋了一个伏笔:
简言之,就是说如果聚集索引较大(或者说表数据量较大),没有完全加载到buffer pool中的话,有可能反而会更慢,还不如用原先的方式. 下面我们来测试下,读取tpcc测试表stock,该表有1亿行记录,表空间文件约65GB,而innodb buffer pool只分配了12G,这时候再看下对比数据: |