2013-08-12 2 views
-1

Вот набор данные:В чем разница между запросами?

Movie (СРЕДНЕЕ, название, год, режиссер) Английский: Существует фильм с ID номером MiD, названием, годом выпуска, и режиссером.

Рецензент (rID, name) Английский: рецензент с идентификационным номером rID имеет определенное имя.

Оценка (rID, mID, stars, ratingDate) Английский: рецензент rID дал фильм mID рейтинг звезд (1-5) на определенном рейтинге.

Задайте вопрос: Найдите названия всех фильмов, у которых нет оценок.

Мой ответ: (возвращает пустое множество)

select title from movie,rating where movie.mid=rating.mid and stars is null 

Правильный ответ:

select title 
from movie 
left join rating using (mID) 
where stars is null 

Я не уверен, что случилось с моим присоединиться? Заранее спасибо!

+0

У вас есть еще одна проблема в вопросе, поэтому у кого-то есть надежда понять это. Что касается проблемы с вашим соединением, вы не пропустите т-ака-сундук ?! –

ответ

1

Вы делаете полное крест-соединение между фильмом и рейтингом. Это означает, что ваш результирующий набор изначально содержит все возможные комбинации (фильм, рейтинг).

Вам требуется movie.mid = rating.mid. Это ограничит ваш результирующий набор только теми (видео, рейтинг), где рейтинг действительно для фильма, в котором он соединен.

Но представьте себе фильм без рейтинга. Это никогда не происходит в таблице рейтинга, поэтому movie.mid = rating.mid также никогда не будет правдой. Поскольку это никогда не бывает так, все фильмы без рейтинга будут удалены из результирующего набора тем условием where where.

Правильный ответ использует left join. Соединение соответствует всем строкам в фильме со всеми строками в рейтингах, которые передают условие объединения (в этом случае mID должен быть равен). Пока это семантически то же самое, что и вы писали. Но тогда вступает в игру часть left: это означает, что для любой строки фильма, где нет , любая строка в рейтингах, которая проходит условие соединения, строка фильма включена в любом случае (один раз) со всеми значениями NULL для таблицы рейтинга колонны. Условие stars is null принимает только строки, сгенерированные эффектом left. (Обратите внимание, что предложение where будет работать только корректно, если stars не может быть пустым в таблице оценок.)

0

Если у фильма нет оценок, rating.mid будет пустым, значит movie.mid=rating.mid будет ложным.

Если у фильма есть рейтинги, то movie.mid=rating.mid будет работать, но (предположительно) stars is null будет ложным.

Так что ваше состояние никогда не будет удовлетворено.

Правильный ответ, который вы опубликовали, потому что условие join является отдельным для состояния where. Сначала таблица movies соединена с таблицей rating, тогда результат отфильтровывается в строки, которые не имеют к ним ничего общего.

Смежные вопросы