count(*)、count(1)、count(column)区别
count(column)
会忽略为 null
的列,其他两个不会。
执行效率
它们三个的效率如何呢?网上说的各有各的理,当表中存在索引和主键的时候(我还没接触过设计表时不设计主键的),三者效率差不多。而我在《高性能MySQL》一书中看到这样一段话:当我们使用 count(*)
时,通配符 * 并不会像我们猜想的那样扩展成所有的列,实际上,它会忽略所有的列而直接统计所有的行数。我们发现最常见的错误就是,在括号内指定一个列却希望统计结果集的行数。如果希望知道的是结果集的行数,最好使用 count(*)
,这样写意义清晰,性能也会很好。
测试
我用100万数据进行测试,发现当且仅当三者有主键时,他们的执行时间几乎相等。
# 有主键:0.139s,无主键:0.283
select count(*) from shop_order
# 有主键:0.154s,无主键:无主键:0.474
select count(id) from shop_order
# 有主键:0.139,无主键:0.285
select count(1) from shop_order
# 有主键但不使用主键:0.383 (count(普通列))
select count(old_id) from shop_order
用75570717条数据进行测试,分别执行两次,测试结果如下
# 第一次:50.660s 第二次:45.891s
select count(*) from tb_mattress_sleep_raw_data
# 第一次:59.925s 第二次:46.948s
select count(`mattress_id`) from tb_mattress_sleep_raw_data
# 第一次:90.997s 第二次:70.314s
select count(`time_zone`) from tb_mattress_sleep_raw_data
关于MyISAM中count函数的小记
另外,在 MyISAM
中,count()
函数总是非常快的,不过这也是有前提条件的,即只有没有任何 where
条件的 count(*)
才非常快,这是这个引擎的特性。