2010-07-01 3 views

Répondre

17

Dans votre exemple, ils devraient faire la même chose. Mais WHERE est traité avantGROUP BY, et donc il n'a pas accès aux valeurs agrégées (c'est-à-dire les résultats des fonctions Min(), Max(), etc.). HAVING est traité aprèsGROUP BY et peut donc être utilisé pour contraindre le jeu de résultats uniquement à ceux dont les valeurs agrégées correspondent à un certain prédicat.

+4

Pour mettre la réponse de Daniel d'une autre manière, la clause where s'applique à toutes les lignes du jeu de résultats. La clause having est appliquée aux groupes créés par une clause group by. Donc, si votre groupe se compose de column1 dans votre exemple et que les conditions étaient sur la colonne 1, alors l'où est le même que l'avoir, puisqu'une ligne est la même que le "groupe". – Anon246

+0

@Strommy: Exactement. Et si pour une raison quelconque vous ne voulez pas utiliser 'HAVING', vous pouvez accomplir la même chose en utilisant un' SELECT' imbriqué et en utilisant la clause 'WHERE 'externe pour exprimer votre prédicat désiré. –

3

Non, car ayant pour fonction d'agrégation ou clause group by.

Par exemple:

SELECT COUNT(ID) 
FROM tablexpto 
where name = 'a' 
having count(ID) > 1 

La première requête ne fonctionnerait pas.

6

HAVING est destiné à être utilisé avec des agrégats, par exemple, HAVING SUM(column1) > 200, WHERE est juste pour les colonnes, par exemple, WHERE column1 < 20.

1

Ne fonctionne qu'avec une clause group by et limite les enregistrements après leur regroupement.

3

Non, ils sont complètement différents. Les conditions de regroupement des fonctions d'agrégation sont les suivantes:

Ils sont calculés après que la valeur agrégée a été calculée.

Exemple:

select id, count(1) 
    from table 
where COND1 
having count(1) > 1 

Ici, la partie having est évaluée après la requête a calculé le nombre (1) La valeur pour chaque groupe.

4

Dans votre exemple, il est le même parce que vous avez pas GROUP BY

Sinon, HAVING est appliqué après GROUP BY qui est appliqué après WHERE ...

Dire que, AYANT avec un filtre simple (x = 2) est exactement le même que WHERE parce que x = 2 n'a de sens que si vous avez groupé dessus. Vous utilisez normalement HAVING sur un agrégat (COUNT(*) > 2 par exemple) qui ne peut être appliqué qu'après GROUP BY

-1

à utiliser vous avoir besoin d'un groupe par article. vous obtiendrez une erreur sans un

+1

Incorrect: si vous utilisez une valeur littérale (c.-à-d. Pas de noms de colonne) dans la clause SELECT et omettez une clause GROUP BY, la clause HAVING sera appliquée à la table entière (ou au resultset filtré si un WHERE clause est utilisée ») et renvoie soit une ligne si la clause' HAVING' est évaluée comme TRUE sinon zéro lignes. Exemple: trouvez s'il y a des trous dans une suite de nombres: 'SELECT 1 FROM Numbers AYANT MAX (num) = COUNT (*);' – onedaywhen

+0

qui était sournois, est-ce que quelqu'un l'utilise dans le monde réel? Comment? – kacalapy

3

Comme d'autres l'ont (la plupart du temps) indiqué à juste titre, dans SQL la clause WHERE est évaluée avant la clause SELECT, donc le résultat d'une fonction de jeu est « hors de portée » dans la clause WHERE.

Par exemple, vous ne pouvez pas faire ceci:

SELECT Subject, MAX(Mark) AS TopScore 
    FROM Exam_Marks 
GROUP 
    BY Subject 
WHERE TopScore <= 70; 

parce que le nom de corrélation de la colonne TopScore n'est pas dans la portée de la clause WHERE.

Bien sûr, nous pourrions utiliser une sous-requête:

SELECT DT1.TopScore 
    FROM (
     SELECT Subject, MAX(Mark) AS TopScore 
      FROM Exam_Marks 
     GROUP 
      BY Subject 
     ) AS DT1 
WHERE DT1.TopScore <= 70; 

Le problème était, au début des implémentations de SQL (à partir avec le système R d'IBM) ne disposaient pas le support des tables dérivées, d'où est né le HAVING unintuitive.

Vous pouvez lire toute l'histoire désolé dans HAVING A Blunderful Time (or Wish You Were WHERE) par Hugh Darwen, à partir de laquelle j'ai emprunté les exemples ci-dessus.

Questions connexes