postgresql查询以确定用户未曾看过的推荐记录

时间:2014-06-30 23:02:28

标签: sql postgresql

我有3个表:user,recommended(post_id,user_id),post

当用户对帖子进行投票时,会使用post_id,user_id和vote值创建新的推荐记录。

我想要一个查询,显示用户尚未看到/投票的随机帖子。

我的想法是,它需要将用户的所有推荐加入到帖子表中......然后选择没有加入推荐的记录。不知道如何做到这一点......

到目前为止,我确实无法工作:

SELECT  "posts".*
FROM "posts"
INNER JOIN "recommendations" ON "recommendations"."post_id" = "posts"."id"
ORDER BY RANDOM()
LIMIT 1

3 个答案:

答案 0 :(得分:2)

您可以使用左外连接执行此操作:

SELECT p.*
FROM posts p  LEFT OUTER JOIN
     recommendations r
     ON r.post_id = p.id and r.userid = YOURUSERID
WHERE r.post_id IS NULL
ORDER BY RANDOM()
LIMIT 1;

请注意,我通过删除双引号(标识符名称不需要)和添加表别名来简化查询。这些更改使查询更容易编写和阅读。

答案 1 :(得分:1)

有几种很好的方法可以排除已经有给定用户推荐的行:
Select rows which are not present in other table

重要的问题是:任意随机
对于任意选择(任何符合条件的行都足够好),这应该是最便宜的:

SELECT *
FROM   posts p
WHERE  NOT EXISTS (
   SELECT 1
   FROM   recommendations 
   WHERE  post_id = p.id
   AND    user_id = $my_user_id
   )
LIMIT  1;

很多帖子的排序步骤可能很昂贵(而且不必要)。在这种使用情况下,大多数帖子通常不会有来自用户的推荐。您每次都必须按random()排序所有这些行 如果任何帖子没有推荐就足够了,那么删除ORDER BY会使速度提高得快。 Postgres可以返回它找到的第一个合格帖子。

答案 2 :(得分:0)

因此您需要一组已推荐的帖子EXCEPT

SELECT p.id FROM posts p
EXCEPT
SELECT r.post_id FROM recommendations r WHERE r.user_id = X
...