0

I have a view with a lot of data. I can got this results using subqueries (data that is ok and optimized):

+------------+
| attendance |
+------------+
|        319 |
|        102 |
|        598 |
|        113 |
|          6 |
|        279 |
|        366 |
|        146 |
|        669 |
|        205 |
|        123 |
+------------+

The next time some user update data, it shows this:

+------------+
| attendance |
+------------+
|        319 |
|        102 |
|        598 |
|        113 |
|          7 |
|        279 |
|        253 |
|        146 |
|        669 |
|        561 |
|        123 |
+------------+

Which is ok, 'cause the user that update the information was the one that before has 6 as attendance.

But the problem comes when I use that data as a temptable and then I make:

 SELECT SUM(attendance) AS total FROM ( /* Subquery returning the above table */)

cause it returns (in the first place with one user having 6 as attendance):

+-------+
| total |
+-------+
|  3169 |
+-------+

And with 7:

+-------+
| total |
+-------+
|  3128 |
+-------+

When it should be 3170!!!

Ideas?

EDIT 1: Pasting the full query.

SELECT SUM(att_member) AS total
FROM
    (SELECT attendance AS att_member
     FROM
         (SELECT id_branch_channel, id_member, attendance, TIMESTAMP, id_event
          FROM view_event_attendance
          WHERE id_event = 782
          ORDER BY TIMESTAMP DESC) AS temptable
     GROUP BY 
              id_member) AS total_attendance_temp

EDIT 2: Pasting the query help I got from here

Select only last value using group by at mysql

Here is the schema of the view.

4

2 回答 2

1

让我们剖析查询,好吗?

我假设 view_event_attendance 对参加活动的每个与会者(成员)都有一个记录。id_event 是该事件的 FK, id_member 是与会者的 FK。您的内部选择为您提供了参加活动 #782 的所有成员的有序列表

SELECT id_branch_channel, id_member, attendance, TIMESTAMP, id_event
FROM view_event_attendance
WHERE id_event = 782
ORDER BY TIMESTAMP DESC

到目前为止,太棒了。现在将此查询包装在另一个查询中:

SELECT attendance AS att_member
FROM (subquery)
GROUP BY id_member

在大多数 SQL dialetcs 中,这只是一个语法错误。MySQL 允许这样做,但结果可能不是您想要的。您将获得参加所述活动的每个 id_member 的出席列。您实际上可能期望的是出席人数的总和,但我在您的问题中没有这么说。在任何情况下,每个选定的字段都应该在您的GROUP BY子句中或使用聚合函数,例如

SELECT SUM(attendance) AS att_member
FROM (subquery)
GROUP BY id_member

或者

SELECT attendance AS att_member
FROM (subquery)
GROUP BY id_member, attendance

话虽如此,我认为没有必要首先使用子查询。假设您想获得上述 SUM,您可以将其重新表述为单个 SQL 查询:

SELECT SUM(attendance) AS att_member
FROM view_event_attendance
WHERE id_event = 782
GROUP BY id_member

如果你想要总数,你可以简单地省略GROUP BY子句,留下这个:

SELECT SUM(attendance) AS att_member
FROM view_event_attendance
WHERE id_event = 782

如果这不能按预期工作,请更详细地描述您实际存储在 view_event_attendance 中的内容,以及您希望第二个查询计算的内容。

于 2013-04-19T21:30:18.667 回答
0

正如@EdGibbs 注意到的那样,子查询返回了错误的结果(我没有注意到)。因此,我再次阅读了我的代码以及我参考的另一个问题的答案,并且现在通过执行以下操作可以正常工作:

SELECT SUM(att_member) AS total
FROM
    (SELECT attendance AS att_member
     FROM
         (SELECT 
            id_branch_channel, 
            id_member, 
            substring(max(concat(from_unixtime(timestamp),attendance)) from 20) as attendance, 
            timestamp, 
            id_event
          FROM view_event_attendance
          WHERE id_event = 782
          GROUP BY id_event, id_member
          ORDER BY timestamp DESC) AS temptable
     ) AS total_attendance_temp

我做的唯一改变是:

  • 使用:substring(max(concat(from_unixtime(timestamp),attendance)) from 20) 作为出勤,而不是仅仅出勤。
  • 在第一个子查询中移动组。

所以问题不在于 MySQL 的 SUM 函数,而在于我的查询。

感谢大家花时间帮助我解决这个问题。你的建议帮助我得到答案。

于 2013-04-19T21:40:09.117 回答