Je me demande comment écrire cette requête.
Je sais que cette syntaxe réelle est fausse, mais elle vous aidera à comprendre ce que je veux. J'en ai besoin dans ce format, car cela fait partie d'une requête beaucoup plus importante.
SELECT distributor_id,
COUNT(*) AS TOTAL,
COUNT(*) WHERE level = 'exec',
COUNT(*) WHERE level = 'personal'
J'ai besoin que tout cela soit retourné dans une seule requête.
En outre, il doit être sur une seule ligne, de sorte que les éléments suivants ne fonctionneront pas:
'SELECT distributor_id, COUNT(*)
GROUP BY distributor_id'
SELECT distributor_id, COUNT(*) AS TOTAL, COUNT(*) WHERE level = 'exec', COUNT(*) WHERE level = 'personal'
Réponses:
Vous pouvez utiliser une
CASE
instruction avec une fonction d'agrégation. C'est fondamentalement la même chose qu'unePIVOT
fonction dans certains SGBDR:la source
COUNT
compteradistributor_id
sage. pas toutes les lignes du tableau, non?Une façon qui fonctionne à coup sûr
EDIT:
Voir la ventilation des performances de @ KevinBalmforth pour savoir pourquoi vous ne voulez probablement pas utiliser cette méthode et devriez plutôt opter pour la réponse de @ Taryn ♦. Je laisse cela pour que les gens puissent comprendre leurs options.
la source
sum(case...)
solution doit être envisagée.group by
avec l'avantage de remplacer une requête imbriquée entière par une simplecount(*)
comme @Mihai le montre - avec d'autres simplifications de syntaxe MySQL uniquement.COUNT
ne compte que lesnon null
valeurs etDECODE
ne renverra de valeur non nulle1
que si votre condition est satisfaite.la source
distributor_id
montrera la requête? Il affiche 1 ligne au total.S'appuyant sur d'autres réponses publiées.
Les deux produiront les bonnes valeurs:
Cependant, les performances sont assez différentes, ce qui sera évidemment plus pertinent à mesure que la quantité de données augmente.
J'ai trouvé que, en supposant qu'aucun index n'était défini sur la table, la requête utilisant les SUM ferait une seule analyse de table, tandis que la requête avec les COUNT ferait plusieurs analyses de table.
Par exemple, exécutez le script suivant:
Mettez en surbrillance les 2 instructions SELECT et cliquez sur l'icône Afficher le plan d'exécution estimé. Vous verrez que la première instruction fera une analyse de table et la seconde fera 4. Évidemment, une analyse de table vaut mieux que 4.
L'ajout d'un index cluster est également intéressant. Par exemple
Le premier SELECT ci-dessus fera une seule analyse d'index en cluster. Le second SELECT effectuera 4 recherches d'index en cluster, mais elles sont toujours plus chères qu'une seule analyse d'index en cluster. J'ai essayé la même chose sur une table avec 8 millions de lignes et le deuxième SELECT était encore beaucoup plus cher.
la source
Pour MySQL, cela peut être raccourci comme suit:
la source
Eh bien, si vous devez tout avoir dans une seule requête, vous pouvez faire une union:
Ou, si vous pouvez le faire après le traitement:
Vous obtiendrez le décompte pour chaque niveau et devrez les résumer tous pour obtenir le total.
la source
UNION
pour être très utile lors de la génération d'un rapport contenant plusieurs instances de laCOUNT(*)
fonction.#1064 - You have an error in your SQL syntax; check the manual that corresponds to your MariaDB server version for the right syntax to use near ') FROM distributors UNION SELECT COUNT() AS EXEC_COUNT FROM distributors WHERE ' at line 1
.Je fais quelque chose comme ça où je donne juste à chaque table un nom de chaîne pour l'identifier dans la colonne A, et un compte pour la colonne. Ensuite, je les ai tous réunis pour qu'ils s'empilent. Le résultat est joli à mon avis - je ne sais pas à quel point il est efficace par rapport aux autres options, mais il m'a donné ce dont j'avais besoin.
Résultat:
la source
a query that I created makes ...
- où est cette requête?Basé sur la réponse acceptée de Bluefeet avec une nuance supplémentaire en utilisant
OVER()
:L'utilisation
OVER()
de rien dans le () vous donnera le nombre total pour l'ensemble de données entier.la source
Je pense que cela peut aussi fonctionner pour vous
select count(*) as anc,(select count(*) from Patient where sex='F')as patientF,(select count(*) from Patient where sex='M') as patientM from anc
et vous pouvez également sélectionner et compter les tables connexes comme celle-ci
select count(*) as anc,(select count(*) from Patient where Patient.Id=anc.PatientId)as patientF,(select count(*) from Patient where sex='M') as patientM from anc
la source