Отображение 0 в запросе счетчика с использованием UNION и подзапроса, присоединение не разрешено - PullRequest
0 голосов
/ 07 ноября 2018

У меня 2 стола (фильмы и часы).

enter image description here

Я хочу знать, какие фильмы смотрят, сколько людей.

Я сделал это:

SELECT movieID, count(persID) FROM watch GROUP BY persID;

Что дает мне в основном то, что я хочу. Единственная проблема заключается в том, что фильмы, которые никто не смотрит, не будут отображаться в моей таблице результатов как 0 зрителей, но они просто исключены.

Я хочу достичь этого двумя разными способами. Используя UNION и другой способ, используя подзапрос .

Ответы [ 4 ]

0 голосов
/ 07 ноября 2018

Использование только UNION:

SELECT movieID, COUNT(*) -1 AS watchCount -- subtract the movie row
FROM
 ( 
    SELECT movieID -- multiple rows per watched movie
    FROM watch
    UNION ALL
    SELECT movieID -- exactly one row per movie
    FROM movies
 )

или (может быть быстрее, если в часах много строк)

SELECT movieID, max(cnt)
FROM
 ( 
    SELECT movieID, count(*) as cnt
    FROM watch
    GROUP BY movieID
    UNION ALL
    SELECT movieID, 0
    FROM movies
 )
GROUP BY movieID
0 голосов
/ 07 ноября 2018

попробуйте сделать это

select movie.title, count(watch.persID) 
from movies left outer join watch on movies.id = watch.movieID 
group by movieID;

Я думаю, что это может сработать

0 голосов
/ 07 ноября 2018

Поскольку вы настаиваете на использовании UNION и подзапроса, вот ответ, который использует оба:

SELECT movieID, COUNT(*) AS watchCount
FROM watch
GROUP BY movieID
UNION
SELECT movieID, 0
FROM movies
WHERE movieID NOT IN (
    SELECT movieID
    FROM watch
    WHERE movieID IS NOT NULL
)
0 голосов
/ 07 ноября 2018

Итак, у вас есть список фильмов, которые вы смотрите, а левый счетчик присоединяет его к списку всех фильмов:

SELECT * FROM
  Movies m
  LEFT JOIN
  (select movieID, count(persID) as countwatch from watch group by persID) w
  ON m.movieid = w.movieid

Левое объединение означает, что вы получаете все фильмы, связанные с количеством только тех, которые смотрят. Если фильм не просматривается, его столбец отсчета будет нулевым

Если вы хотите превратить ноль в 0, используйте COALESCE:

SELECT m.*, COALESCE(w.countwatch, 0) as countwatch FROM
  Movies m
  LEFT JOIN
  (select movieID, count(persID) as countwatch from watch group by persID) w
  ON m.movieid = w.movieid

Есть много способов, которыми мы могли бы выполнить этот запрос, но я специально выбрал этот способ, потому что он основывается на том, что вы уже сделали и знаете, и обрисовывает в общих чертах, как мы можем сгруппировать и обобщить данные на подуровне, а затем подключить их к больше данных на внешнем уровне

Это также полезно, потому что вы можете добавить некоторые дополнительные данные, например, из таблицы продаж, чтобы узнать, какие фильмы, которые вы смотрите, являются самыми прибыльными. Если вы выберете маршрут Салмана (который является правильным в этом контексте), вы столкнетесь с проблемами со статистикой, поскольку добавляете больше таблиц, потому что номера строк будут умножаться больше, чем вы ожидаете. Группируя, например, продажи и отслеживание в подзапросах, вы можете присоединить их к основной таблице, не вызывая дублирования строк (также называемых декартовым продуктом). В результате для запросов такого рода я склонен предлагать группирование и агрегирование в подзапросах, прежде чем объединять их с другими таблицами, чтобы сохранить соотношение 1: 1 между основной таблицей (фильмами) и выходными данными подзапросов (например, просмотр, продажа, количество актеров). и т. д.) которые содержат данные, относящиеся к основному фильму, но не обязательно связанные друг с другом

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...