2014-01-23 3 views
1

Я написал эту часть SQL для получения фильмов с персонами (role_id = 1 - это режиссер). В то время как фильм имеет одного режиссера - все хорошо, но появляются дополнительные строки с таким же названием фильма, когда есть более чем один режиссер.Согласованный результат с внутренним соединением

SELECT 
    m.name, 
    ps.name as director 
FROM 
    movies m 
INNER JOIN participants p ON 
    m.movie_id = p.movie_id 
INNER JOIN persones ps ON 
    ps.person_id = p.person_id AND 
    p.role_id = 1  
ORDER BY m.updated_at DESC 
LIMIT 10\G 

Например

*************************** 1. row *************************** 
    name: Film1 
director: director1 
*************************** 2. row *************************** 
    name: Film1 
director: director2 
*************************** 3. row *************************** 
    name: Film1 
director: director3 
*************************** 4. row *************************** 
    name: Film2 
director: director4 
*************************** 5. row *************************** 
    name: Film2 
director: director5 
*************************** 6. row *************************** 
    name: Film2 
director: director6 

ОК, я нашел GROUP_CONCAT для конкатенации директоров в одной строке

SELECT 
    m.name, 
    GROUP_CONCAT(ps.name SEPARATOR ", ") as director 
FROM 
    movies m 
INNER JOIN participants p ON 
    m.movie_id = p.movie_id 
INNER JOIN persones ps ON 
    ps.person_id = p.person_id AND 
    p.role_id = 1  
ORDER BY m.updated_at DESC 
LIMIT 10\G 

, но у меня есть неожиданный результат!

*************************** 1. row *************************** 
    name: Film123 
director: director1, someperson1, someperson3, ......, someperson18 

Всего одна строка с людьми из другой категории (артисты или частица). Даже строка с фильмом имеет имя не то же самое, что и ORDER BY m.updated_at DESC должен вернуть

ответ

1

Вы пропали без вести с GROUP BY вы используете групповую функцию, но без группировки их

SELECT 
    m.name, 
    GROUP_CONCAT(ps.name SEPARATOR ", ") as director 
FROM 
    movies m 
INNER JOIN participants p ON 
    m.movie_id = p.movie_id 
INNER JOIN persones ps ON 
    ps.person_id = p.person_id AND 
    p.role_id = 1  
GROUP BY m.name /* or you can use the movie id column here*/ 
ORDER BY m.updated_at DESC 
LIMIT 10 

GROUP_CONCAT(expr)

GROUP BY (Aggregate) Functions

EDIT Также убедитесь, что у вас есть movie_id в вашем movies таблица

SELECT 
    m.movie_id , 
    m.international_name AS o_name, 
    m.description AS description, 
    m.name AS name, 
    m.covers AS covers, 
    m.YEAR AS YEAR, 
    m.updated_at AS added, 
    GROUP_CONCAT(ps.name SEPARATOR ', ') AS director 
FROM 
    movies AS m 
INNER JOIN movies_genres AS mgen ON 
    (m.movie_id = mgen.movie_id) 
INNER JOIN participants p ON 
    m.movie_id = p.movie_id 
INNER JOIN persones ps ON 
    ps.person_id = p.person_id AND 
    p.role_id = 1 /* Directors */ 
WHERE 
    m.hidden=0 AND 
    mgen.genre_id = 6 AND 

GROUP BY m.name 
ORDER BY m.updated_at DESC 
+0

Это небольшое дополнение к другому, более сложному запросу. Когда я добавляю это, MYSQL возвращает ошибку: ERROR 1054 (42S22): Неизвестный столбец «m.movie_id» в разделе «on». Полный запрос там: http://pastebin.com/U0WVMfC6 – Neka

+0

@Neka см. Мой обновленный ответ, а также рассмотрите возможность использования [** fiddle **] (http://sqlfiddle.com/) с соответствующим набором данных, чтобы он был диагностировать реальную проблему –

+1

Удивительный! Благодаря!! – Neka

0

Если вы используете GROUP_CONCAT, вы должны использовать GROUP BY для создания групп.

SELECT 
m.name, 
GROUP_CONCAT(ps.name SEPARATOR ", ") as director 
FROM 
    movies m 
INNER JOIN participants p ON 
    m.movie_id = p.movie_id 
INNER JOIN persones ps ON 
    ps.person_id = p.person_id AND 
    p.role_id = 1  
GROUP BY m.movie_id,m.name 
ORDER BY m.updated_at DESC 
LIMIT 10 
Смежные вопросы