加入4个表with group by,2 having和where子句

Posted

tags:

篇首语:本文由小常识网(cha138.com)小编为大家整理,主要介绍了加入4个表with group by,2 having和where子句相关的知识,希望对你有一定的参考价值。

我的数据库由4个表组成:

  1. 用户(id,“姓名”,姓氏,生日)
  2. 友谊(userid1,userid2,“timestamp”)
  3. 帖子(id,userid,“text”,“timestamp”)
  4. 喜欢(postid,userid,“timestamp”)

我需要在2018年1月之间获得一组具有3个以上友谊的独特用户名,并且他们的“喜欢”平均每个“帖子”的范围为[10; 35)。

我在第一步写了这句话:

select  distinct u."name"
from users u
join friendships f on u.id = f.userid1
where f."timestamp" between '2018-01-01'::timestamp and '2018-01-31'::timestamp
group by u.id
having count(f.userid1) > 3;

它工作正常,返回3行。但是当我以这种方式添加第二部分时:

select  distinct u."name"
from users u
join friendships f on u.id = f.userid1
join posts p on p.userid = u.id
join likes l on p.id = l.postid
where f."timestamp" between '2018-01-01'::timestamp and '2018-01-31'::timestamp
group by u.id
having count(f.userid1) > 3 
    and ((count(l.postid) / count(distinct l.postid)) >= 10 
        and (count(l.postid) / count(distinct l.postid)) < 35);

我疯了94行。我不知道为什么。将感谢可能的帮助。

答案

您在distinct中不需要u.name,因为聚合将删除副本。

select
   u."name"
from 
   users u
   inner join friendships f on u.id = f.userid1
   inner join posts p on u.id = p.userid
   inner join likes l on p.id = l.postid
where 
   f."timestamp" >= '2018-01-01'::timestamp 
   and f."timestamp" < '2018-02-01'::timestamp
group by 
    u."name"
having 
    count(distinct f.userid1) > 3 
    and ((count(l.postid) / count(distinct l.postid)) >= 10 
            and (count(l.postid) / count(distinct l.postid)) < 35);

正如评论所述。当你使用betweendate做范围时,不是一个好主意。

f."timestamp" >= '2018-01-01'::timestamp 
and f."timestamp" < '2018-02-01'::timestamp

会给你一个月的整月。

另一答案

试试下面!使用“count(f.userid1)> 3”的问题在于,如果用户具有例如2个朋友和6个帖子以及3个喜欢他们将得到2 x 6 = 12行,所以有12个非空f.userid1的记录。通过计算不同的f.userid2,您可以统计不同的朋友。对于用于过滤的其他计数也会出现类似问题。

select  u."name"
from users u
join friendships f on u.id = f.userid1
join posts p on p.userid = u.id
left join likes l on p.id = l.postid
where f."timestamp" > '2018-01-01'::timestamp and f."timestamp" < '2018-02-01'::timestamp
group by u.id, u."name"
having
 --at least three distinct friends
 count( distinct f.userid2) > 3 
  --distinct likes / distinct posts
  --we use l.* to count distinct likes since there's no primary key
  and ((count(distinct l.*) / count(distinct p.id)) >= 10 
        and ((count(distinct l.*) / count(distinct p.id)) < 35);

以上是关于加入4个表with group by,2 having和where子句的主要内容,如果未能解决你的问题,请参考以下文章

带有 2 个表的 SQL Server GROUP BY

group by&having&where

从 2 个表中 SELECT 到 dataGridView 时的 GROUP BY 问题

使用带有 SUM 和 GROUP BY 的完整 JOIN 避免重复条目

使用 group by 从一个包含批量记录的表中获取一些统计数据并将结果放入第二个表中

从 3 个表中选择,在两个 group by 之前有两个 order by