MySQLではなく自分で作成した列(たとえばselect 1 as "number"
)を配置する必要があるのはなぜですか?HAVING
WHERE
WHERE 1
そして、(列名の代わりに定義全体を書く)代わりに欠点はありますか?
MySQLではなく自分で作成した列(たとえばselect 1 as "number"
)を配置する必要があるのはなぜですか?HAVING
WHERE
WHERE 1
そして、(列名の代わりに定義全体を書く)代わりに欠点はありますか?
MySQLのWHEREではなく、HAVINGの後に自分で作成した列(たとえば、「数値として1を選択」)を配置する必要があるのはなぜですか?
WHERE
の前GROUP BY
にHAVING
適用され、後に適用されます(そして集計でフィルタリングできます)。
一般に、これらの句のどちらでもエイリアスを参照できませんが、、、およびでレベルのエイリアスをMySQL
参照できます。SELECT
GROUP BY
ORDER BY
HAVING
また、「WHERE 1」(列名の代わりに定義全体を記述する)を実行する代わりに、欠点はありますか?
計算された式に集計が含まれていない場合は、それをWHERE
句に入れる方がおそらく効率的です。
この質問に対する他のすべての回答は、重要なポイントに当てはまりませんでした。
テーブルがあると仮定します。
CREATE TABLE `table` (
`id` int(10) unsigned NOT NULL AUTO_INCREMENT,
`value` int(10) unsigned NOT NULL,
PRIMARY KEY (`id`),
KEY `value` (`value`)
) ENGINE=InnoDB DEFAULT CHARSET=utf8
そして、IDと値の両方が1から10までの10行があります。
INSERT INTO `table`(`id`, `value`) VALUES (1, 1),(2, 2),(3, 3),(4, 4),(5, 5),(6, 6),(7, 7),(8, 8),(9, 9),(10, 10);
次の2つのクエリを試してください。
SELECT `value` v FROM `table` WHERE `value`>5; -- Get 5 rows
SELECT `value` v FROM `table` HAVING `value`>5; -- Get 5 rows
まったく同じ結果が得られます。このHAVING
句はGROUPBY句なしでも機能することがわかります。
違いは次のとおりです。
SELECT `value` v FROM `table` WHERE `v`>5;
上記のクエリはエラーを発生させます:エラー#1054-'where句'の不明な列'v'
SELECT `value` v FROM `table` HAVING `v`>5; -- Get 5 rows
WHERE
句を使用すると、条件で任意のテーブル列を使用できますが、エイリアスや集計関数を使用することはできません。
HAVING
句を使用すると、条件で選択した(!)列、エイリアス、または集計関数を使用できます。
これは、WHERE
句が選択前にデータをフィルタリングするのに対し、HAVING
句は選択後に結果のデータをフィルタリングするためです。
したがってWHERE
、テーブルに多数の行がある場合は、条件を句に入れる方が効率的です。
EXPLAIN
主な違いを確認してみてください。
EXPLAIN SELECT `value` v FROM `table` WHERE `value`>5;
+----+-------------+-------+-------+---------------+-------+---------+------+------+--------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+-------+---------------+-------+---------+------+------+--------------------------+
| 1 | SIMPLE | table | range | value | value | 4 | NULL | 5 | Using where; Using index |
+----+-------------+-------+-------+---------------+-------+---------+------+------+--------------------------+
EXPLAIN SELECT `value` v FROM `table` having `value`>5;
+----+-------------+-------+-------+---------------+-------+---------+------+------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+-------+-------+---------------+-------+---------+------+------+-------------+
| 1 | SIMPLE | table | index | NULL | value | 4 | NULL | 10 | Using index |
+----+-------------+-------+-------+---------------+-------+---------+------+------+-------------+
どちらWHERE
かを表示するかHAVING
、インデックスを使用しますが、行は異なります。
主な違いは、WHERE
グループ化されたアイテム(などSUM(number)
)では使用できないのに対し、HAVING
使用できることです。
その理由は、グループ化の前WHERE
に行われ、グループ化が行われた後に行われるためです。HAVING
HAVING
の集計をフィルタリングするために使用されますGROUP BY
。
たとえば、重複する名前を確認するには、次のようにします。
SELECT Name FROM Usernames
GROUP BY Name
HAVING COUNT(*) > 1
これらの2つは、データをフィルタリングするための条件について両方が言うために使用されるため、最初と同じように感じられます。いずれの場合も、「where」の代わりに「having」を使用できますが、「having」の代わりに「where」を使用できない場合があります。これは、selectクエリでは、「where」は「select」の前にデータをフィルタリングし、「having」は「select」の後にデータをフィルタリングするためです。したがって、実際にはデータベースにないエイリアス名を使用する場合、「where」はそれらを識別できませんが、「having」は識別できます。
例:テーブルStudentにstudent_id、name、birthday、addressを含めるようにします。birthdayのタイプがdateであると想定します。
SELECT * FROM Student WHERE YEAR(birthday)>1993; /*this will work as birthday is in database.if we use having in place of where too this will work*/
SELECT student_id,(YEAR(CurDate())-YEAR(birthday)) AS Age FROM Student HAVING Age>20;
/*this will not work if we use ‘where’ here, ‘where’ don’t know about age as age is defined in select part.*/
WHEREはデータがグループ化される前にフィルタリングし、HAVINGはデータがグループ化された後にフィルタリングします。これは重要な違いです。WHERE句によって削除された行は、グループに含まれません。これにより、計算された値が変更される可能性があり、その結果(=結果として)、 HAVING 句でのこれらの値の使用に基づいてフィルタリングされるグループに影響を与える可能性があります。
そして続けて、
HAVINGはWHEREに非常に似ているため、 GROUP BYが指定されていない場合、ほとんどのDBMSはそれらを同じものとして扱います。それでも、自分でその区別をする必要があります。HAVINGは、 GROUPBY句と組み合わせてのみ使用してください 。標準の行レベルのフィルタリングにはWHEREを使用します。
抜粋: フォルタ、ベン。「SamsTeachYourselfSQL in 10 Minutes(5th Edition)(Sams Teach Yourself ...)」
持つことは集約でのみ使用されますが、非集約ステートメントではどこで使用されますか?単語が集約の前にそれを置く場所がある場合(group by)