简体   繁体   English

mysql连接多个表并计数查询

[英]mysql join with multiple tables and count query

I have total 6 tables in which different info has been saved 我总共有6个表格,其中保存了不同的信息

Now i need a result in which get count from 5 tables and select all info from main table but if record does not exist than it must be need to return 0 instead of no row found that's the problem here 现在我需要一个从5个表中获取计数并从主表中选择所有信息的结果,但是如果记录不存在,那么它必须需要返回0而不是没有找到行,这就是这里的问题

I have tried below query but didn't get success 我已经尝试过下面的查询,但是没有成功

SELECT 
    u.*,
    COUNT(DISTINCT  c.id) as comments,
    COUNT(DISTINCT d.id) as dislikes,
    COUNT(DISTINCT l.id) as likes,
    COUNT(DISTINCT s.id) as shares,
    COUNT(DISTINCT t.id) as tags
FROM 
    job_details as u
    JOIN job_comments as c ON u.id = c.job_id
    JOIN job_dislike as d ON u.id = d.job_id
    JOIN job_like as l ON u.id = l.job_id
    JOIN job_share as s ON u.id = s.job_id
    JOIN job_tags as t ON u.id = t.job_id
WHERE 
    u.id = c.job_id AND
    u.id = d.job_id AND
    u.id = l.job_id AND
    u.id = s.job_id AND
    u.id = t.job_id

GROUP BY 
    u.id

This query is executed, but didn't get exact result. 该查询已执行,但未获得确切结果。 I don't quite understand why. 我不太明白为什么。

I was hoping somebody here could help me out? 我希望这里有人可以帮助我吗?

Thanks! 谢谢!

Use LEFT JOIN instead of JOIN . 使用LEFT JOIN代替JOIN and you don't need WHERE clause since you have joined those tables. 并且由于加入了这些表,因此不需要WHERE子句。 And, use IFNULL function to return 0 for null values. 并且,使用IFNULL函数为空值返回0。 You need to modify you query like this : 您需要像这样修改查询:

SELECT u.id,
    IFNULL(COUNT(DISTINCT  c.id),0) as comments,
    IFNULL(COUNT(DISTINCT d.id),0) as dislikes,
    IFNULL(COUNT(DISTINCT l.id),0) as likes,
    IFNULL(COUNT(DISTINCT s.id),0) as shares,
    IFNULL(COUNT(DISTINCT t.id),0) as tags
FROM job_details as u
    LEFT JOIN job_comments as c ON u.id = c.job_id
    LEFT JOIN job_dislike as d ON u.id = d.job_id
    LEFT JOIN job_like as l ON u.id = l.job_id
    LEFT JOIN job_share as s ON u.id = s.job_id
    LEFT JOIN job_tags as t ON u.id = t.job_id
GROUP BY u.id

You probably didn't get the exact result because some tables may be missing values. 您可能没有得到确切的结果,因为某些表可能缺少值。

Although you can solve this problem with a LEFT JOIN , the safer solution is to pre-aggregate the data: 尽管您可以使用LEFT JOIN解决此问题,但更安全的解决方案是预先聚合数据:

SELECT u.*, c.comments, d.dislikes, l.likes, s.shares, t.tags
FROM job_details as u LEFT JOIN
     (select c.job_id, count(*) as comments from job_comments group by c.job_id
     ) c
     ON u.id = c.job_id LEFT JOIN
     (select d.job_id, count(*) as dislikes from job_dislike d group by d.job_id
     ) d
     ON u.id = d.job_id LEFT JOIN
     (select l.job_id, count(*) as likes from job_like l group by l.job_id
     ) l
     ON u.id = l.job_id LEFT JOIN
     (select s.job_id, count(*) as shares from job_share s group by s.job_id
     ) s
     ON u.id = s.job_id LEFT JOIN
     (select t.job_id, count(*) as tags from job_tags t group by t.job_id
     ) t
     ON u.id = t.job_id;

Why is this better? 为什么这样更好? Consider an id that has 5 comments, likes, dislikes, shares and tags. 考虑具有5个评论,喜欢,不喜欢,分享和标签的ID。 The JOIN approach produces an intermediate result with 5*5*5*5*5 = 3,125 intermediate rows. JOIN方法产生一个中间结果,其中5 * 5 * 5 * 5 * 5 = 3,125个中间行。 Things can really get out of hand for popular ids. 对于流行的ID,事情真的可能会失控。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM