2015-02-24 3 views
1

в моей базе данных MySQL У меня есть три таблицы:MySQL: Граф в других таблицах

CREATE TABLE favorites (
    id int(11) NOT NULL AUTO_INCREMENT, 
    user_id int(11) NOT NULL, 
    location_id int(11) NOT NULL, 
    PRIMARY KEY (id) 
); 


CREATE TABLE locations (
    id int(20) NOT NULL, 
    `name` varchar(150) NOT NULL, 
    pos_lat float NOT NULL, 
    pos_lon float NOT NULL, 
    PRIMARY KEY (id) 
); 


CREATE TABLE ratings (
    id int(11) NOT NULL AUTO_INCREMENT, 
    location_id int(11) NOT NULL, 
    user_id int(11) NOT NULL 
    stars int(11) NOT NULL, 
    review text, 
    PRIMARY KEY (id) 
); 

Теперь я хочу, чтобы выбрать некоторые из мест, и подсчитать количество оценок, среднее количество звезд и количество фаворитами в эффективном режиме.

Мой подход этот, но он дает мне совершенно неправильные значения для COUNT.

SELECT l.id AS location_id, 
COUNT(DISTINCT r.id), AVG(r.stars), COUNT(DISTINCT f.id) 
FROM locations l, ratings r, favorites f 
WHERE (l.id=r.location_id OR l.id=f.location_id) 
AND l.id IN (7960,23713,...,18045,24247) 
GROUP BY l.id 

Вы можете мне помочь?

+0

А в чем проблема с вашим запросом? – Jens

ответ

0

Проблема связана с вашим условием соединения с помощью OR:

WHERE (l.id=r.location_id OR l.id=f.location_id) 

Когда он находит одну записи, где l.id = r.location_id это будет справедливо для всех строк в е из-за OR. Аналогично, когда он найдет 1 запись с l.id = f.location_id, вы будете соответствовать всем строкам в r.

Вместо этого используйте LEFT JOIN для каждого из r и f:

SELECT l.id AS location_id, 
COUNT(DISTINCT r.id), AVG(r.stars), COUNT(DISTINCT f.id) 
FROM locations l 
LEFT JOIN ratings r ON (l.id = r.location_id) 
LEFT JOIN favorites f ON (l.id = f.location_id) 
WHERE l.id IN (7960,23713,...,18045,24247) 
GROUP BY l.id 
+0

Работает отлично. Спасибо! –

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