简体   繁体   English

在 MySQL 中按日期获取累积数据

[英]Get accumulated data by dates in MySQL

I need to get accumulated number of users by a range of dates ie for a month by date.我需要按日期范围获取累积的用户数,即按日期计算一个月。 The following query works fine but I have to run it for each date and I cannot use group by date.以下查询工作正常,但我必须为每个日期运行它,我不能使用按日期分组。 Please advise.请指教。

  1. MySQL version 8 MySQL 版本8
  2. Sample Data样本数据
+------------------------+
| id | Registration_Date |
+------------------------+
| 1  | 2020-05-01        | 
| 2  | 2020-05-01        |
| 3  | 2020-05-02        |
| 4  | 2020-05-03        |
| 5  | 2020-05-04        |
+------------------------+
  1. Current Query当前查询
SELECT COUNT(id) AS 'Registrations'
FROM users
WHERE DATE(Registration_Date) <= "2020-05-04";
  1. Desired Result期望的结果
+-----------------------------------+
| Registration_Date | Registrations |
+-----------------------------------+
| 2020-05-01        | 2             |
| 2020-05-02        | 3             |
| 2020-05-03        | 4             |
| 2020-05-04        | 5             |
+-----------------------------------+

You can use window functions to achieve the result you want, COUNT ing id values on or before the current registration date.您可以使用 window 函数来实现您想要的结果,在当前注册日期或之前COUNT ing id值。 Note we use DISTINCT to avoid duplication of entries where multiple users register on the same day:请注意,我们使用DISTINCT来避免多个用户在同一天注册的重复条目:

SELECT DISTINCT Registration_Date,
       COUNT(id) OVER (ORDER BY Registration_Date) AS Registrations
FROM users

Output: Output:

Registration_Date   Registrations
2020-05-01          2
2020-05-02          3
2020-05-03          4
2020-05-04          5

Demo on dbfiddle dbfiddle 上的演示

To deal with the case where there are registrations before the first reporting date of interest, you need to count registrations up to and including the first date and then for each date in the reporting period in a derived table, and then sum those in an outer query:为了处理在第一个感兴趣的报告日期之前有注册的情况,您需要在派生表中计算直到第一个日期(包括第一个日期)的注册,然后在报告期间的每个日期计算,然后在一个外部表中汇总这些注册。询问:

SELECT Reporting_Date,
       SUM(Registrations) OVER (ORDER BY Reporting_Date) AS Registrations
FROM (
  SELECT '2020-05-01' AS Reporting_Date, COUNT(id) AS Registrations
  FROM users
  WHERE Registration_Date <= '2020-05-01'
  UNION 
  SELECT Registration_Date, COUNT(id)
  FROM users
  WHERE Registration_Date BETWEEN '2020-05-02' AND '2020-05-04'
  GROUP BY Registration_Date
) r

Generating the result this way in general will be more efficient than wrapping the original query as a derived table as it will require fewer aggregations.以这种方式生成结果通常比将原始查询包装为派生表更有效,因为它需要更少的聚合。

Demo on dbfiddle dbfiddle 上的演示

I used Nick 's answer as source and now modified it a bit to get grand total plus daily increment value.我使用Nick的答案作为来源,现在对其进行了一些修改以获得总计加上每日增量值。

SELECT Reporting_Date, Registrations FROM

(SELECT DISTINCT DATE(Registration_Date) AS Reporting_Date,
       COUNT(id) OVER (ORDER BY DATE(Registration_Date)) AS Registrations
FROM users) AS RAW_Result

WHERE Reporting_Date BETWEEN "2020-05-01" AND "2020-05-04";

Result:结果:

+-----------------------------------+
| Registration_Date | Registrations |
+-----------------------------------+
| 2020-05-01        | 1200          | (grand total until this date)
| 2020-05-02        | 1201          | (grand total + daily increment) 
| 2020-05-03        | 1202          |
| 2020-05-04        | 1203          |
+-----------------------------------+

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

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