在數據庫中Count(*)或者Count(1)或者Count([列])或許是最常用的聚合函數。很多人其實對這三者之間是區分不清的。本文會闡述這三者的作用,關系以及背后的原理。
我在網上看到一些所謂的優化說建議不使用Count(* )而是使用Count(1),從而可以提升性能,給出的理由是Count( *)會帶來全表掃描。而實際上如何寫Count並沒有區別。
Count(1)和Count(*)實際上的意思是,評估Count(XXX)中的表達式XXX是否為NULL,如果為NULL則不計數,而非NULL則會計數。比如我們看代碼1所示,在Count中指定NULL(優化器不允許顯式指定NULL,因此需要賦值給變量才能指定)。
select count(null) from tableA t;
其中表tableA中不存在一整行的值都為空的。所以結果全不計數為0。
select count(*) from tableA t;
select count(1) from tableA t;
不管Count(*) 或者Count(1)或者無論Count(XXX)時結果都會一樣,因為這些值都不為NULL。
因此,count(*)和count(1)最大的區別有:
1、count(*)會帶來全表掃描(效率低)
2、count(*)與count(1)都包括null統計
3、count(column)不包括null統計
4、count(1)和count(主鍵) 這兩個只掃描主鍵Index就可以得到數據,或者說count(ROWID)這也是只掃描Index的(效率高),
這個問題就是問你什么時候Oracle容易走表查詢,什么時候Oracle容易走INDEX查詢。
實際應用中,你得看實際情況,沒准這個表沒有唯一鍵索引呢?在CBO(ORACLE提供的一種SQL優化器)的情況下,統計情報不准確呢?
因此,如果某個表上Count(*)用的比較多時,考慮在一個最短的列建立一個單列索引,會極大的提升性能。