GROUP BY ба HAVING
Өмнөх хичээлд нэгтгэх функцүүдийг бүх мөрт нэг дор ашиглаж сурлаа. Гэхдээ "хэрэглэгч тус бүр хэдий дүнд захиалга хийсэн бэ?" эсвэл "статус тус бүрт хэдэн захиалга байна вэ?" гэсэн асуултад GROUP BY хэрэгтэй болдог. Энэ бол нэгтгэх функцүүдийн хамгийн хүчирхэг хослол юм.
GROUP BY — бүлэглэн нэгтгэх
GROUP BY нь хүснэгтийн мөрүүдийг тодорхой талбарын утгаар бүлэглэж, тус бүр дээр нэгтгэх функц ажиллуулдаг.
Өмнөх хичээлийн orders хүснэгтийг ашиглая:
-- Статус тус бүрт хэдэн захиалга байгааг тоол
SELECT status, COUNT(*) AS захиалгын_тоо
FROM orders
GROUP BY status;
Үр дүн:
| status | захиалгын_тоо | |--------|--------------| | completed | 4 | | pending | 1 | | cancelled | 1 |
-- Хэрэглэгч тус бүрийн нийт захиалгын дүн
SELECT customer, SUM(amount) AS нийт_дүн
FROM orders
GROUP BY customer
ORDER BY нийт_дүн DESC;
GROUP BY-н дараа ORDER BY ашиглаж үр дүнг эрэмбэлж болно. Дээрх жишээнд хамгийн их дүнтэй хэрэглэгч эхэнд харагдана.
GROUP BY-г олон талбараар ашиглах
Нэгэн зэрэг хэд хэдэн талбараар бүлэглэж болно:
-- Хэрэглэгч, статусаар бүлэглэх
SELECT
customer,
status,
COUNT(*) AS тоо,
SUM(amount) AS нийт_дүн
FROM orders
GROUP BY customer, status
ORDER BY customer, status;
SELECT-д байгаа нэгтгэх функц биш бүх талбар GROUP BY-д заавал байх ёстой гэдгийг санаарай — энэ бол нийтлэг алдаа юм.
HAVING — бүлэгт нөхцөл тавих
WHERE нь бүлэглэхийн өмнө мөрүүдийг шүүдэг. Харин HAVING нь бүлэглэсний дараа тооцооны үр дүнг шүүдэг.
-- 2-оос дээш захиалга хийсэн хэрэглэгчдийг олох
SELECT customer, COUNT(*) AS тоо
FROM orders
GROUP BY customer
HAVING COUNT(*) > 1;
-- Үр дүн: Болд — 2
-- Нийт дүн 20000-аас дээш бүлэгүүдийг харуулах
SELECT customer, SUM(amount) AS нийт_дүн
FROM orders
GROUP BY customer
HAVING SUM(amount) > 20000
ORDER BY нийт_дүн DESC;
WHERE ба HAVING-г хослуулах
WHERE болон HAVING-г нэг асуулгад хамт ашиглаж болно:
-- Зөвхөн "completed" захиалгуудаас бүлэглэж,
-- нийт дүн нь 30000-аас дээш хэрэглэгчдийг олох
SELECT
customer,
COUNT(*) AS захиалгын_тоо,
SUM(amount) AS нийт_дүн
FROM orders
WHERE status = 'completed'
GROUP BY customer
HAVING SUM(amount) > 30000
ORDER BY нийт_дүн DESC;
SQL асуулгын гүйцэтгэлийн дараалал санах нь чухал:
FROM → WHERE → GROUP BY → HAVING → SELECT → ORDER BY
WHERE нь бүлэглэхийн өмнө, HAVING нь бүлэглэсний дараа ажилладаг учраас хоёрыг хольж болохгүй.
Дараагийн хичээлд:
Асуулгын доторх асуулга буюу subquery-г ашиглаж, нэг SELECT-н үр дүнг нөгөөд оролт болгон дамжуулж сурна.