在一个连接表上使用组合条件加入

时间:2012-12-09 20:03:14

标签: sql postgresql join

我加入了一个将歌曲加入到流派中的表格。该表有一个“源”列,用于标识类型的找到位置。类型可以从博客,艺术家,标签和帖子中找到。

所以,

songs | song_genre                 | genres 
id    | song_id, source, genre_id  | id

我想要构建的歌曲是一个类似于此的歌曲SELECT查询,因为我已经有了一个genre_id:

IF exists song_genre with source='artist' AND a song_genre with source='blog'
OR exists song_genre with source='artist' AND a song_genre with source='post'
OR exists song_genre with source='tag'

我打算通过做一些连接来做到这一点,但我确定我做得不好。

使用Postgres 9.1。

2 个答案:

答案 0 :(得分:3)

kgu87的查询是正确的,但可能产生一个相对昂贵的计划,其中包含大量的子选择计数。所有这些计数都可以通过源代码casegroup by song_id的流派表格一次性累积。没有样本数据,很难说这是否更快,但我怀疑它可能。无论如何,我认为它更简单。

select g.song_id
from song_genre g
group by g.song_id
having
  ( sum(case when g.source = 'tag' then 1 else 0 end) > 0 )
  or
  ( sum(case when g.source = 'artist' then 1 else 0 end) > 0
    and (
      sum(case when g.source = 'blog' then 1 else 0 end) > 0
      or
      sum(case when g.source = 'post' then 1 else 0 end) > 0
    )
  )

答案 1 :(得分:1)

select id
from
(
    select distinct
    id,
    (
        select
        count(*) from
        song_genre b
        where a.id = b.song_id
        and b.source = 'artist'
    ) as artist,
    (
        select
        count(*) from
        song_genre b
        where a.id = b.song_id
        and b.source = 'blog'
    ) as blog,
    (
        select
        count(*) from
        song_genre b
        where a.id = b.song_id
        and b.source = 'post'
    ) as post,
    (
        select
        count(*) from
        song_genre b
        where a.id = b.song_id
        and b.source = 'tag'
    ) as tag
    from songs A
) AA
where
(AA.artist > 0 AND AA.blog > 0)
OR
(AA.artist > 0 AND AA.post > 0)
OR
(AA.tag > 0)