![](/img/trans.png)
[英]select from one mysql table where ids match results from select of another mysql table
[英]Select all ids in one table that match at least as many ids in another table
如果我有这样的表结构
[movies]---<[movies_genres]>---[genres]---<[users_genres]>---[users]
给定一个user.id
,我想查询仅与users_genres.genre_id
共享其类型的users_genres.genre_id
。
更清楚的是,如果用户喜欢{科幻,动作和浪漫片}类型,而电影是{科幻,动作和恐怖片},则不应退还该电影。 但是,如果电影只是{sci-fi}或{sci-fi,动作},则应将其返回。 因此,如果其流派未在用户的首选流派中列出,则不应将其退回。
我该怎么做呢?
谢谢。
编辑:
我尝试过的东西
select movies_id from movies_genres mg
where mg.genres_id not in (
select genres_id from users_genres ug
where ug.users_id = 1
)
编辑2:
好的,我已经修复了上面的代码,我认为它似乎可以正常工作
select * from movies
where movies.id not in (
select movies_id from movies_genres mg
where mg.genres_id not in (
select genres_id from users_genres ug
where ug.users_id = 2
)
)
我基本上是在玩减集(我认为)。 这对我来说都是很新的,所以我什至不清楚SQL在这里是如何工作的。 就是这样,如果我可以从另一个中减去一个集合,结果结果是空的,那是一个子集。 这基本上满足了我对movie_genres作为users_genres的子集的要求。
一个join
和aggregation
应在表之间的工作:
select mg.movie_id
from user_genres ug left join
movie_genres mg
on mg.genre_id = ug.genre_id
where ug.user_id = ?
group by mg.movie_id
having count(*) = count(ug.genre_id); -- do all match
编辑:
如果您只需要完全匹配,那么一种简单的方法是创建一个流派列表并在其上进行匹配:
select mg.movie_id
from (select mg.movie_id, group_concat(mg.genre_id order by mg.genre_id) as genres
from movie_genres mg
group by mg.movie_id
) mg join
(select group_concat(ug.genre_id order by ug.genre_id) as genres
from user_genres ug
where ug.user_id = ?
) ug
on mg.genres = ug.genres;
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.