Je suis simplement curieux de connaître la syntaxe SQL. Donc si j'ai
SELECT
itemName as ItemName,
substring(itemName, 1,1) as FirstLetter,
Count(itemName)
FROM table1
GROUP BY itemName, FirstLetter
Ce serait incorrect car
GROUP BY itemName, FirstLetter
devrait vraiment être
GROUP BY itemName, substring(itemName, 1,1)
Mais pourquoi ne pouvons-nous pas simplement utiliser le premier pour plus de commodité?
Réponses:
SQL est implémenté comme si une requête était exécutée dans l'ordre suivant:
Pour la plupart des systèmes de bases de données relationnelles, cet ordre explique quels noms (colonnes ou alias) sont valides car ils doivent avoir été introduits à une étape précédente.
Ainsi, dans Oracle et SQL Server, vous ne pouvez pas utiliser un terme dans la clause GROUP BY que vous définissez dans la clause SELECT car le GROUP BY est exécuté avant la clause SELECT.
Il y a cependant des exceptions: MySQL et Postgres semblent avoir une intelligence supplémentaire qui le permet.
la source
GROUP BY substring(itemName, 1,1)
, la base de données est-elle suffisamment intelligente pour ne pas prendre le coup de performance de recalculer la sous-chaîne dans la clause SELECT?sql_mode
sans inclure ONLY_FULL_GROUP_BY dans le masque de bits, l'optimiseur a une chance de fournir de meilleurs résultats avec une utilisation variée / différente de l'alias dans laHAVING
clause.Vous pouvez toujours utiliser une sous-requête pour pouvoir utiliser l'alias; Bien sûr, vérifiez les performances (il est possible que le serveur de base de données exécute les deux de la même manière, mais ne fait jamais de mal à vérifier):
la source
Au moins dans PostgreSQL, vous pouvez utiliser le numéro de colonne dans le jeu de résultats dans votre clause GROUP BY:
Bien sûr, cela commence à être pénible si vous faites cela de manière interactive et que vous modifiez la requête pour changer le nombre ou l'ordre des colonnes dans le résultat. Mais reste.
la source
GROUP BY FirstLetter
est autorisé dans Postgresql. Pour savoir, essayez d'exécuter ceci dans Postgresql: sélectionnez la sous-chaîne (nom_table, 1,2) comme tname à partir du groupe information_schema.tables par tnameGROUP BY
une expression qui contient des fonctions d'agrégation ou des fonctions de fenêtre, ce qui "évidemment" ne fonctionne pas.SQL Server ne vous permet pas de référencer l'alias dans la clause GROUP BY en raison de l'ordre logique de traitement. La clause GROUP BY est traitée avant la clause SELECT, de sorte que l'alias n'est pas connu lorsque la clause GROUP BY est évaluée. Cela explique également pourquoi vous pouvez utiliser l'alias dans la clause ORDER BY.
Voici une source d'informations sur les phases de traitement logique de SQL Server .
la source
Je ne réponds pas pourquoi il en est ainsi, mais je voulais seulement montrer un moyen de contourner cette limitation dans SQL Server en utilisant
CROSS APPLY
pour créer l'alias. Vous l'utilisez ensuite dans laGROUP BY
clause, comme ceci:la source
Attention, l'utilisation d'alias dans Group By (pour les services qui le prennent en charge, comme postgres) peut avoir des résultats inattendus. Par exemple, si vous créez un alias qui existe déjà dans l'instruction interne, le Group By choisira le nom du champ interne.
la source
Certains SGBD vous permettront d'utiliser un alias au lieu d'avoir à répéter l'expression entière.
Teradata en est un exemple.
J'évite la notation de position ordinale comme recommandé par Bill pour des raisons documentées dans cette question SO .
L'alternative simple et robuste consiste à toujours répéter l'expression dans la clause GROUP BY.
DRY ne s'applique PAS à SQL.
la source
Méfiez-vous des alias lors du regroupement des résultats d'une vue dans SQLite. Vous obtiendrez des résultats inattendus si le nom d'alias est le même que le nom de colonne de toutes les tables sous-jacentes (pour les vues.)
la source
À l'époque, j'ai découvert que Rdb, l'ancien produit DEC maintenant pris en charge par Oracle, permettait d'utiliser l'alias de colonne dans le GROUP BY. Oracle Mainstream jusqu'à la version 11 n'autorise pas l'utilisation de l'alias de colonne dans GROUP BY. Je ne sais pas ce que Postgresql, SQL Server, MySQL, etc. autoriseront ou non. YMMV.
la source