2011-08-13 65 views
3

我有3个表:singerssongs,albums。他们都与singer_idMySQL LEFT JOIN多表逻辑问题

即使没有匹配singer_id我需要得到他们所有人。我设法让所有的人都与此查询:

SELECT singers.singer_name, albums.album_name, songs.song_name 
    FROM singers 
LEFT JOIN albums ON singers.singer_id = albums.singer_id 
LEFT JOIN songs ON albums.singer_id = songs.singer_id 
    WHERE singer_id = ? 

但问题是,我可以;吨正确显示的结果。

假设歌手有3张专辑和11首歌曲。我这是怎么显示出来......

显示歌手名称:

echo $results[0]['singer_name'] 

显示歌曲名称:

foreach($results as $song) { 
    // PROBLEM: instead of getting 11 songs i'm getting 33 results so each song show up 3 times. 
    echo $song['song_name'] 
} 

显示专辑:

foreach($results as $album) { 
// PROBLEM: i'm getting 33 albums instead of 3 each album shows up 3 times. 
    echo $album['album_name'] 
} 

编辑: 歌曲表参照专辑表album_id但是第是没有专辑的歌曲,所以我需要得到的结果只是由singer_id

我需要得到的是: 11首歌曲。 3张专辑。 1名歌手。

在此先感谢。编辑: 这个解决方案为我工作。 我想要的是获得指定歌手ID和专辑的所有歌曲 我想要的结果看起来像这样。

singer_name : song_name  : album_name 
............................................................... 
Jay Z  : 99 Problems : NULL 
Jay Z  : Gotta Have It : Watch the Throne 

所以我想让所有歌手的歌曲即使他们没有在任何专辑呢。

这是我使用的查询。

SELECT singers.singer_name, songs.song_name, albums.album_name 
FROM singers 
LEFT JOIN songs ON singers.singer_id = songs.singer_id 
LEFT JOIN albums ON albums.album_id = songs.album_id 
WHERE singers.singer_id = ? 

感谢@ knittl我得到了我需要的结果。

但现在还有另一个问题。 我有3张专辑和11首歌曲

歌曲显示正常,但是当我在做专辑一foreach循环,我再次得到33张专辑....

我怎样才能正确显示相册?我只有3张专辑。

+0

使用该逻辑,您将获得交叉连接。一首歌也应该与特定专辑相关 - 你得到的是与每张专辑相关的每首歌曲的列表。 – GalacticCowboy

+0

@GalacticCowboy:逻辑,是的 - 但不是提供的LEFT JOIN'd查询。无论哪种方式,查询都会返回大量垃圾数据。 –

+0

#galacticcowboy我知道我可以参考歌曲的专辑,但是有没有专辑附加到他们的歌曲呢。 – ParparDromi

回答

2

你想要的所有歌曲。从歌曲中选择并执行左连接以从其他表中获取潜在数据(按顺序获得更好的表示):

SELECT a.artist_name, COALESCE(b.album_name, '(no album)'), s.song_name, 
FROM songs s 
LEFT JOIN artists a 
ON s.singer_id = a.singer_id 
LEFT JOIN albums b 
ON s.album_id = b.album_id AND s.singer_id = b.singer_id 
ORDER BY a.artist_name, b.album_id 
+0

感谢这是一个很好的解决方案,但我现在有另一个问题。看看我的编辑。 – ParparDromi

+0

@parpardromi:请为此类问题开个新问题。我已经回答了类似的问题:[只显示更改值](http://stackoverflow.com/questions/1459201/array-how-to-display-the-changing-values-only/1459239#1459239) – knittl

+0

谢谢我将开始一个新的问题。 – ParparDromi

0

你想最主要的是歌曲,一首歌曲必须有一个艺术家,但可能有/或没有专辑:

SO:

SELECT  singers.singer_name, IF('' == albums.album_name, 'single', albums.album_name) AS album_name, songs.song_name 
FROM  songs AS songs 
RIGHT JOIN singers AS singers ON (singers.singer_id = songs.singer_id) 
LEFT JOIN albums AS albums ON (albums.singer_id = songs.singer_id) 
WHERE  songs.singer_id = ? 
+0

什么是'单个'字符串? – ParparDromi

+0

该查询不显示没有艺术家的歌曲。也应该避免加入连接,因为它们降低了可维护性。 – Arjan