Quelle est la différence entre select count (*) et select count (any_non_null_column)?

58

Il me semble me souvenir que (sur Oracle) il y a une différence entre prononcer select count(*) from any_tableet select count(any_non_null_column) from any_table.

Quelles sont les différences entre ces deux déclarations, le cas échéant?

Martin
la source

Réponses:

72
  • COUNT (*) comprendra NULLS
  • COUNT (column_or_expression) ne le fera pas.

Cela signifie que vous COUNT(any_non_null_column)obtiendrez la même chose que COUNT(*)bien sûr car il n'y a pas de valeur NULL pouvant causer des différences.

En règle générale, COUNT(*)devrait être mieux car tout index peut être utilisé car COUNT(column_or_expression)ne peut être indexé ou SARGable

À partir de ANSI-92 (recherchez " Scalar expressions 125")

Cas:

a) Si COUNT (*) est spécifié, le résultat est la cardinalité de T.

b) Sinon, laissez TX être le tableau à colonne unique résultant de l'application de l'expression <value expression> à chaque ligne de T et de l'élimination des valeurs nulles. Si une ou plusieurs valeurs nulles sont éliminées, une condition d'achèvement est alors créée: warning - valeur nulle éliminée dans la fonction set.

Les mêmes règles sont applicables à SQL Server et Sybase aussi au moins

Remarque: COUNT (1) est identique à COUNT (*) car 1 est une expression non Nullable.

gbn
la source
4
Juste pour être complet: Oracle utilisera une analyse d'index sur une colonne indexée non NULL si elle count(*)est utilisée.
a_horse_with_no_name
Je pensais que les trois options possibles étaient COUNT(*), COUNT(<constant>)et COUNT(<column name>)que toutes les trois pourraient être préfixées par ALLou DISTINCT(par défaut à ALLomises). Je me demande simplement quelle expression peut être utilisée où vous dites _or_expression?
onedaywhen
2
@onedayQuand COUNT(1)un exemple inutile, c'est le même que COUNT(*). COUNT(CASE WHEN a>b THEN 1 END)à titre d'exemple, qui compte les lignes où a> b.
Ypercubeᵀᴹ
16

Dans toute version récente (c.-à-d. 8.x + ) d’Oracle, ils font la même chose . En d'autres termes, la seule différence est sémantique:

select count(*) from any_table

est facile à lire et à comprendre ce que vous essayez de faire, et

select count(any_non_null_column) from any_table

est plus difficile à lire parce que

  1. c'est plus long
  2. c'est moins reconnaissable
  3. vous devez réfléchir à savoir si any_non_null_columnest vraiment appliquée commenot null

En bref, utilisezcount(*)

Jack Douglas
la source
9

Dans une version récente, il n'y a en effet aucune différence entre count (*) et count ( toute colonne non nulle ), l'accent étant mis sur not null :-) J'ai accessoirement couvert ce sujet avec un article de blog: Est-ce que count (col) vaut mieux que count (*)

Uwe Hesse
la source
1

Dans le livre Oracle8i Certified Professional Guide d’examen de certification DBA (ISBN 0072130601) , page 78 indique que COUNT (1) sera plus rapide que COUNT (*), car certains mécanismes sont mis en œuvre pour vérifier le dictionnaire de données pour la nullité de chaque colonne (ou au moins la première colonne avec non-nullability) lorsqu’on utilise COUNT (*) . COUNT (1) contourne ces mécanismes.

MySQL triche pour 'SELECT COUNT (1) on tblname;' sur les tables MyISAM en lisant l’en-tête du nombre de tables. InnoDB compte à chaque fois.

Pour tester si COUNT (1) fonctionnera plus vite que COUNT (*) d'une manière agnostique à la base de données, il suffit d'exécuter ce qui suit et d'évaluer le temps d'exécution par vous-même:

SELECT COUNT(1) FROM tblname WHERE 1 = 1;
SELECT COUNT(*) FROM tblname WHERE 1 = 1;
SELECT COUNT(column-name) FROM tblname WHERE 1 = 1;

Cela permet à la fonction COUNT de fonctionner sur le même pied d'égalité, quel que soit le moteur de stockage ou le SGBDR.

RolandoMySQLDBA
la source
8
Le guide d'examen est faux. Dans Oracle, nombre (*) = nombre (1) (au moins après la version 7). See asktom.oracle.com/pls/asktom/… (Déjà référencé par @JackPDouglas)
Leigh Riffel
3
Intéressant. COUNT (*) ne doit absolument pas vérifier les colonnes conformément à la spécification ANSI. A été demandé sur le SO pour SQL Server il y a quelque temps trop stackoverflow.com/questions/1221559/count-vs-count1/...
gbn
@gbn, @Leigh Riffel, @bernd_k Merci de m'avoir rappelé et de me rappeler de lire et d'en apprendre plus, en particulier parce que je ne travaille pas avec Oracle depuis un moment.
RolandoMySQLDBA