Skip to main content

count

count是什么

count是一个聚合函数,用于统计符合查询条件的记录中,非NULL的记录数量。

而负责判断是否为NULL值的逻辑通常是在引擎层实现的。

count(1)和count(id)区别

count中指定不同类型的值,其执行过程是不一样的。

count(id)-主键索引

  • 当只有主键索引时:数据库存储引擎(innodb)会遍历所有的行,并返回id,然后count执行+1
  • 当存在非主键索引时:优化器会优先选择非主键索引进行遍历,因为相比于主键索引,非主键索引体积更小,查询效率更高

count(1)

  • 当只有主键索引时:数据库存储引擎(innodb)会遍历所有的记录,但不读取记录中的任何字段,因为count参数为1,他永远是非空的。因此server层每从innodb读取到一条记录,就会count+1
  • 当存在非主键索引时:会优先选择非主键索引

count(*)

  • 优化器会做一定的优化,等同于count(0)

count(col)

  • 会执行全表扫描,并由引擎层判断数据是否非空,根据返回具体数据字段是否非空,再

通过对比count(1)和count(id),我们可以发现,count(1)比count(id)少了一个步骤,那就是不需要读取记录中的具体字段值并判断是否非空。

因此count(1)的效率会高于count(id)。

为什么MySQL不维护一个最终记录数

以存储引擎innodb为例。存储引擎支持事务,由于多版本并发控制的原因,具体存在多少行,是需要在一个事务中实时计算的。

如何优化count

对于需要频繁统计数量的大表,可以在单独维护一张count表,记录具体表的数量。