loading..
Русский    English
01:57
листать

Упражнение 37 (подсказки и решения)

Рассмотрим следующее решение задачи, которое свободно от ошибок, проанализированных в пункте 3.2:

Консоль
Выполнить
  1. SELECT t1.class
  2. FROM (SELECT a.class AS class, COUNT(b.name) AS coun
  3.       FROM Classes a LEFT JOIN
  4.            Ships b ON b.class = a.class
  5.       GROUP BY a.class
  6.       UNION ALL
  7.       SELECT a1.class AS class, COUNT(ship) AS coun
  8.       FROM Classes a1 LEFT JOIN
  9.            Outcomes d ON d.ship = a1.class
  10.       WHERE d.ship NOT IN (SELECT b.name
  11.                            FROM Ships b
  12.                            )
  13.       GROUP BY a1.class
  14.       ) t1
  15. GROUP BY t1.class
  16. HAVING SUM(t1.coun) = 1;

Действительно, в подзапросе объединяются два запроса, первый из которых подсчитывает для каждого класса корабли из таблицы Ships, а второй подсчитывает только те головные корабли, которых нет в Ships. Затем основной запрос для каждого класса эти количества суммирует и оставляет только те классы, в которых содержится только один корабль.

Обратите внимание на использование UNION ALL. Это необходимо, т. к. в противном случае будут устранены дубликаты пары {класс, количество кораблей}, в результате чего будет выводиться класс, для которого имеется один неголовной корабль в Ships и головной в Outcomes. Как раз эта характерная ошибка отмечалась нами в пункте 3.2.

Что же осталось исправить, раз это решение не принимается системой? Причина состоит в том, что головной корабль класса может принимать участие в нескольких сражениях, и тогда второй из объединяемых запросов столько раз учтет один и тот же головной корабль, сколько раз тот участвовал в сражениях.

Вернуться к обсуждению упражнения 37

Решить задачу на SQL-EX.RU

Bookmark and Share
Тэги:
ALL AND AUTO_INCREMENT AVG battles CASE CAST CHAR CHARINDEX CHECK classes COALESCE Convert COUNT CROSS APPLY CTE DATEDIFF DATENAME DATEPART DATETIME DDL DEFAULT DELETE DISTINCT DML EXCEPT EXISTS EXTRACT FROM FULL JOIN GROUP BY Guadalcanal HAVING IDENTITY IN INNER JOIN insert INTERSECT IS NOT NULL ISNULL laptop LEFT LEFT OUTER JOIN LEN maker MAX MIN MONTH MySQL NOT Больше тэгов
Учебник обновлялся
месяц назад
©SQL-EX,2008 [Развитие] [Связь] [О проекте] [Ссылки] [Team]
Перепечатка материалов сайта возможна только с разрешения автора.
Rambler's Top100