【问题标题】:mysql joining 3 tables with a group by group bymysql 通过 group by 加入 3 个表
【发布时间】:2018-03-01 08:59:01
【问题描述】:

我有三张桌子

users:

+----+--------+--------------+
| id | name   | user_type_id |
+----+--------+--------------+
|  1 | Tawsif |            1 |
|  2 | Karim  |            2 |
+----+--------+--------------+
transactions:
+----+---------+--------+
| id | user_id | amount |
+----+---------+--------+
|  1 |       1 |     10 |
|  2 |       2 |     10 |
|  3 |       1 |     10 |
+----+---------+--------+
course_fee:
+----+---------+-----+
| id | user_id | fee |
+----+---------+-----+
|  1 |       1 | 105 |
|  2 |       2 |  33 |
|  3 |       1 | 106 |
+----+---------+-----+

我想从交易和课程费用表中获取总行数、每个用户交易金额和费用的总和

所以我尝试了这个

SELECT users.id, SUM(transactions.amount) as total_transaction_amount,
count(transactions.id) as transaction_count, 
sum(course_fee.fee) as total_fee, 
count(course_fee.user_id) as total_fee_count 
    FROM users 
INNER join transactions on transactions.user_id = users.id 
INNER join course_fee on course_fee.user_id = users.id 
    GROUP by users.id

结果:

+----+--------------------------+-------------------+-----------+-----------------+
| id | total_transaction_amount | transaction_count | total_fee | total_fee_count |
+----+--------------------------+-------------------+-----------+-----------------+
|  1 |                       40 |                 4 |       422 |               4 |
|  2 |                       10 |                 1 |        33 |               1 |
+----+----------

它返回了错误的结果。我该如何解决这个问题?

【问题讨论】:

    标签: mysql join group-by


    【解决方案1】:

    您的问题是在尝试从多个与联接相关的表中报告聚合时出现的常见问题。一种明智的处理方法是加入两个单独的子查询,每个子查询分别汇总交易和费用:

    SELECT
        u.id,
        u.name,
        COALESCE(t.amount, 0) AS total_transaction_amount,
        COALESCE(t.cnt, 0)    AS transaction_count,
        COALESCE(c.fee, 0)    AS total_fee,
        COALESCE(c.cnt, 0)    AS total_fee_count
    FROM users u
    LEFT JOIN
    (
        SELECT user_id, COUNT(*) AS cnt, SUM(amount) AS amount
        FROM transactions
        GROUP BY user_id
    ) t
        ON u.id = t.user_id
    LEFT JOIN
    (
        SELECT user_id, COUNT(*) AS cnt, SUM(fee) AS fee
        FROM course_fee
        GROUP BY user_id
    ) c
        ON u.id = c.user_id;
    

    请注意,我们在上面留下了连接,因为用户可能不会出现在交易或费用表中。在这种情况下,我们为总和和计数分配零值。

    【讨论】:

    • 我的答案一个连接查询。不确定您的想法。
    • 哎呀抱歉...我在检查 stackoverflow 时太累了.. 再次感谢
    【解决方案2】:

    正确答案

       SELECT test.id,transaction_count,test.total_transaction_amount, 
        IFNULL(SUM(course_fee.fee),0) AS total_fee, 
        IFNULL(COUNT(course_fee.user_id),0) AS total_fee_count  FROM 
        (
          SELECT users.id, IFNULL(SUM(transactions.amount),0) AS 
          total_transaction_amount,
          IFNULL(COUNT(transactions.id),0) AS transaction_count
          FROM users 
          LEFT JOIN transactions ON transactions.user_id = users.id 
          GROUP BY users.id
        ) AS test 
        LEFT JOIN course_fee ON course_fee.user_id = test.id 
        GROUP BY test.id
    

    这是2nd JOIN 之后的查询中发生的情况,这就是为什么 id 1 得到 40

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2020-12-08
      • 1970-01-01
      • 1970-01-01
      • 2011-09-26
      • 2012-01-07
      • 1970-01-01
      • 2017-11-14
      • 1970-01-01
      相关资源
      最近更新 更多