2.7. ÐгÑегаÑнÑе ÑÑнкÑии
Ðак болÑÑинÑÑво дÑÑгиÑ
ÑеÑвеÑов ÑелÑÑионнÑÑ
баз даннÑÑ
, Postgres Pro поддеÑÐ¶Ð¸Ð²Ð°ÐµÑ Ð°Ð³ÑегаÑнÑе ÑÑнкÑии. ÐгÑегаÑÐ½Ð°Ñ ÑÑнкÑÐ¸Ñ Ð²ÑÑиÑлÑÐµÑ ÐµÐ´Ð¸Ð½ÑÑвенное знаÑение, обÑабаÑÑÐ²Ð°Ñ Ð¼Ð½Ð¾Ð¶ÐµÑÑво ÑÑÑок. ÐапÑимеÑ, еÑÑÑ Ð°Ð³ÑегаÑнÑе ÑÑнкÑии, вÑÑиÑлÑÑÑие: count (колиÑеÑÑво), sum (ÑÑммÑ), avg (ÑÑеднее), max (макÑимÑм) и min (минимÑм) Ð´Ð»Ñ Ð½Ð°Ð±Ð¾Ñа ÑÑÑок.
РпÑимеÑÑ, Ð¼Ñ Ð¼Ð¾Ð¶ÐµÐ¼ найÑи ÑамÑÑ Ð²ÑÑокÑÑ Ð¸Ð· вÑÐµÑ Ð¼Ð¸Ð½Ð¸Ð¼Ð°Ð»ÑнÑÑ Ð´Ð½ÐµÐ²Ð½ÑÑ ÑемпеÑаÑÑÑ:
SELECT max(temp_lo) FROM weather;
max ----- 46 (1 row)
ÐÑли Ð¼Ñ Ñ Ð¾Ñим ÑзнаÑÑ, в каком гоÑоде (или гоÑÐ¾Ð´Ð°Ñ ) наблÑдалаÑÑ ÑÑа ÑемпеÑаÑÑÑа, можно попÑобоваÑÑ:
SELECT city FROM weather WHERE temp_lo = max(temp_lo); ÐÐÐÐÐ ÐРно ÑÑо не бÑÐ´ÐµÑ ÑабоÑаÑÑ, Ñак как агÑегаÑнÑÑ ÑÑнкÑÐ¸Ñ max нелÑÐ·Ñ Ð¸ÑполÑзоваÑÑ Ð² пÑедложении WHERE. (ÐÑо огÑаниÑение обÑÑÑнÑеÑÑÑ Ñем, ÑÑо пÑедложение WHERE должно опÑеделиÑÑ, Ð´Ð»Ñ ÐºÐ°ÐºÐ¸Ñ
ÑÑÑок вÑÑиÑлÑÑÑ Ð°Ð³ÑегаÑнÑÑ ÑÑнкÑиÑ, Ñак ÑÑо оно, оÑевидно, должно вÑÑиÑлÑÑÑÑÑ Ð´Ð¾ агÑегаÑнÑÑ
ÑÑнкÑий.) Ðднако как ÑаÑÑо бÑваеÑ, запÑÐ¾Ñ Ð¼Ð¾Ð¶Ð½Ð¾ пеÑезапÑÑÑиÑÑ Ð¸ полÑÑиÑÑ Ð¶ÐµÐ»Ð°ÐµÐ¼Ñй ÑезÑлÑÑаÑ, пÑименив подзапÑоÑ:
SELECT city FROM weather
WHERE temp_lo = (SELECT max(temp_lo) FROM weather);
city
---------------
San Francisco
(1 row)
ТепеÑÑ Ð²ÑÑ Ð² поÑÑдке â подзапÑÐ¾Ñ Ð²ÑполнÑеÑÑÑ Ð¾ÑделÑно и ÑезÑлÑÑÐ°Ñ Ð°Ð³ÑегаÑной ÑÑнкÑии вÑÑиÑлÑеÑÑÑ Ð²Ð½Ðµ завиÑимоÑÑи Ð¾Ñ Ñого, ÑÑо пÑоиÑÑ Ð¾Ð´Ð¸Ñ Ð²Ð¾ внеÑнем запÑоÑе.
ÐгÑегаÑнÑе ÑÑнкÑии Ñакже оÑÐµÐ½Ñ Ð¿Ð¾Ð»ÐµÐ·Ð½Ñ Ð² ÑоÑеÑании Ñ Ð¿Ñедложением GROUP BY. ÐапÑимеÑ, Ð¼Ñ Ð¼Ð¾Ð¶ÐµÐ¼ полÑÑиÑÑ Ð¼Ð°ÐºÑимÑм минималÑной дневной ÑемпеÑаÑÑÑÑ Ð² ÑазÑезе гоÑодов:
SELECT city, max(temp_lo)
FROM weather
GROUP BY city;
city | max
---------------+-----
Hayward | 37
San Francisco | 46
(2 rows)
ÐдеÑÑ Ð¼Ñ Ð¿Ð¾Ð»ÑÑаем по одной ÑÑÑоке Ð´Ð»Ñ ÐºÐ°Ð¶Ð´Ð¾Ð³Ð¾ гоÑода. ÐаждÑй агÑегаÑнÑй ÑезÑлÑÑÐ°Ñ Ð²ÑÑиÑлÑеÑÑÑ Ð¿Ð¾ ÑÑÑокам ÑаблиÑÑ, ÑооÑвеÑÑÑвÑÑÑим оÑделÑÐ½Ð¾Ð¼Ñ Ð³Ð¾ÑодÑ. ÐÑ Ð¼Ð¾Ð¶ÐµÐ¼ оÑÑилÑÑÑоваÑÑ Ð³ÑÑппиÑÑемÑе ÑÑÑоки, иÑполÑзÑÑ HAVING, и подÑÑиÑÑваемÑе ÑÑÑоки, иÑполÑзÑÑ FILTER:
SELECT city, max(temp_lo), count(*) FILTER (WHERE temp_lo < 30)
FROM weather
GROUP BY city
HAVING max(temp_lo) < 40;city | max | count ---------+-----+------- Hayward | 37 | 5 (1 row)
ÐÑ Ð¿Ð¾Ð»ÑÑаем Ñе же ÑезÑлÑÑаÑÑ, но ÑолÑко Ð´Ð»Ñ ÑеÑ
гоÑодов, где вÑе знаÑÐµÐ½Ð¸Ñ temp_lo менÑÑе 40. ÐаконеÑ, еÑли Ð½Ð°Ñ Ð¸Ð½ÑеÑеÑÑÑÑ ÑолÑко гоÑода, Ð½Ð°Ð·Ð²Ð°Ð½Ð¸Ñ ÐºÐ¾ÑоÑÑÑ
наÑинаÑÑÑÑ Ñ Â«S», Ð¼Ñ Ð¼Ð¾Ð¶ÐµÐ¼ ÑделаÑÑ:
SELECT city, max(temp_lo), count(*) FILTER (WHERE temp_lo < 30)
FROM weather
WHERE city LIKE 'S%' -- (1)
GROUP BY city
HAVING max(temp_lo) < 40;ÐпеÑаÑÐ¾Ñ |
Ðажно понимаÑÑ, как ÑооÑноÑÑÑÑÑ Ð°Ð³ÑегаÑнÑе ÑÑнкÑии и SQL-пÑÐµÐ´Ð»Ð¾Ð¶ÐµÐ½Ð¸Ñ WHERE и HAVING. ÐÑновное оÑлиÑие WHERE Ð¾Ñ HAVING заклÑÑаеÑÑÑ Ð² Ñом, ÑÑо WHERE ÑнаÑала вÑбиÑÐ°ÐµÑ ÑÑÑоки, а заÑем гÑÑппиÑÑÐµÑ Ð¸Ñ
и вÑÑиÑлÑÐµÑ Ð°Ð³ÑегаÑнÑе ÑÑнкÑии (Ñаким обÑазом, она оÑбиÑÐ°ÐµÑ ÑÑÑоки Ð´Ð»Ñ Ð²ÑÑиÑÐ»ÐµÐ½Ð¸Ñ Ð°Ð³ÑегаÑов), Ñогда как HAVING оÑбиÑÐ°ÐµÑ ÑÑÑоки гÑÑпп поÑле гÑÑппиÑовки и вÑÑиÑÐ»ÐµÐ½Ð¸Ñ Ð°Ð³ÑегаÑнÑÑ
ÑÑнкÑий. Ðак ÑледÑÑвие, пÑедложение WHERE не должно ÑодеÑжаÑÑ Ð°Ð³ÑегаÑнÑÑ
ÑÑнкÑий; не Ð¸Ð¼ÐµÐµÑ ÑмÑÑла иÑполÑзоваÑÑ Ð°Ð³ÑегаÑнÑе ÑÑнкÑии Ð´Ð»Ñ Ð¾Ð¿ÑÐµÐ´ÐµÐ»ÐµÐ½Ð¸Ñ ÑÑÑок Ð´Ð»Ñ Ð²ÑÑиÑÐ»ÐµÐ½Ð¸Ñ Ð°Ð³ÑегаÑнÑÑ
ÑÑнкÑий. ÐÑедложение HAVING, напÑоÑив, вÑегда ÑодеÑÐ¶Ð¸Ñ Ð°Ð³ÑегаÑнÑе ÑÑнкÑии. (СÑÑого говоÑÑ, Ð²Ñ Ð¼Ð¾Ð¶ÐµÑе напиÑаÑÑ Ð¿Ñедложение HAVING, не иÑполÑзÑÑ Ð°Ð³ÑегаÑÑ, но ÑÑо Ñедко бÑÐ²Ð°ÐµÑ Ð¿Ð¾Ð»ÐµÐ·Ð½Ð¾. То же Ñамое ÑÑловие Ð¼Ð¾Ð¶ÐµÑ ÑабоÑаÑÑ Ð±Ð¾Ð»ÐµÐµ ÑÑÑекÑивно на ÑÑадии WHERE.)
РпÑедÑдÑÑем пÑимеÑе Ð¼Ñ Ñмогли пÑимениÑÑ ÑилÑÑÑ Ð¿Ð¾ Ð½Ð°Ð·Ð²Ð°Ð½Ð¸Ñ Ð³Ð¾Ñода в пÑедложении WHERE, Ñак как Ð½Ð°Ð·Ð²Ð°Ð½Ð¸Ñ Ð½Ðµ нÑжно агÑегиÑоваÑÑ. Такой ÑилÑÑÑ ÑÑÑекÑивнее, Ñем дополниÑелÑное огÑаниÑение HAVING, поÑÐ¾Ð¼Ñ ÑÑо Ñ Ð½Ð¸Ð¼ не пÑиÑ
одиÑÑÑ Ð³ÑÑппиÑоваÑÑ Ð¸ вÑÑиÑлÑÑÑ Ð°Ð³ÑегаÑÑ Ð´Ð»Ñ Ð²ÑеÑ
ÑÑÑок, не ÑдовлеÑвоÑÑÑÑиÑ
ÑÑÐ»Ð¾Ð²Ð¸Ñ WHERE.