Рыбы с суммарным уловом на дату d менее n

26. Найти рыб с суммарным уловом на дату меньше заданного значения

Условие задачи:
Есть таблицы:

  • fish(id, name) — виды рыб;

  • catch(id, fish_id, dt, quantity) — данные об улове.

Необходимо вывести названия рыб, для которых суммарный улов на дату d меньше значения n.


Спойлеры к решению

Подсказки
💡 Отфильтруй записи по дате d.
💡 Суммарный улов можно посчитать через SUM(quantity).
💡 Для фильтрации агрегированного результата используй HAVING.
💡 Если рыба, которую в этот день вообще не ловили, тоже должна считаться как улов 0, понадобится LEFT JOIN и COALESCE.

Решение

Если учитывать только рыб, у которых были записи об улове на указанную дату:

SELECT f.name
FROM fish f
JOIN catch c
    ON c.fish_id = f.id
WHERE c.dt = :d
GROUP BY f.id, f.name
HAVING SUM(c.quantity) < :n;

WHERE оставляет уловы только за нужную дату, после чего SUM(c.quantity) считает их суммарное количество для каждой рыбы.

Если нужно учитывать также рыб, которых в эту дату вообще не ловили, их суммарный улов следует считать равным 0:

SELECT
    f.name
FROM fish f
LEFT JOIN catch c
    ON c.fish_id = f.id
   AND c.dt = :d
GROUP BY f.id, f.name
HAVING COALESCE(SUM(c.quantity), 0) < :n;

Важно условие по дате разместить в ON, а не в WHERE. Иначе строки рыб без улова будут исключены после LEFT JOIN.

COALESCE преобразует NULL, полученный для рыб без записей об улове, в 0.