SQL Server每天统计邮件数

SQL Server每天统计邮件数,sql,sql-server,Sql,Sql Server,我正在使用SQL Server,我有下表: tbl_Message: id, date, group_id 这是一个包含消息的表:它的id、发送日期、发送组。 我正在计算每天收到的邮件数量。我对它进行了查询,但它不会在没有消息的情况下返回天。查询是: SELECT DATEADD(MINUTE, DATEDIFF(MINUTE, 0, date)/1440 * 1440,0) AS dateDay, COUNT(*) AS countMsgDay FROM tbl_Message WHERE

我正在使用SQL Server,我有下表:

tbl_Message:
id, date, group_id
这是一个包含消息的表:它的id、发送日期、发送组。 我正在计算每天收到的邮件数量。我对它进行了查询,但它不会在没有消息的情况下返回天。查询是:

SELECT DATEADD(MINUTE, DATEDIFF(MINUTE, 0, date)/1440 * 1440,0) AS dateDay,
COUNT(*) AS countMsgDay
FROM tbl_Message
WHERE group_id = 1
GROUP BY DATEADD(MINUTE, DATEDIFF(MINUTE, 0, date)/1440 * 1440,0)
例如:

对于tbl_消息

id |     date                 | group_id
----------------------------------------
1  | 2014-10-01 21:04:00.000  | 1
2  | 2014-10-03 21:09:00.000  | 1
查询返回:

dateDay                    | countMsgDay
---------------------------------
2014-10-01 00:00:00.000    | 1
2014-10-03 00:00:00.000    | 1
我想要的是:

dateDay                    | countMsgDay
---------------------------------
2014-10-01 00:00:00.000    | 1
2014-10-02 00:00:00.000    | 0
2014-10-03 00:00:00.000    | 1

此问题的正常解决方案是生成所有天数的数据,然后使用
左连接。您可以通过以下几种方式生成天数:

  • 使用日历表
  • 使用递归CTE
  • 使用数字表
  • 在查询中显式地包含日期
在某些情况下,有一种更简单的解决方案,即条件聚合。这假设每天至少有一条记录。然后,您可以为此目的使用条件聚合:

SELECT CAST(date as DATE) as dateDay,
       SUM(CASE WHEN group_id = 1 THEN 1 ELSE 0 END) as countMsgDay
FROM tbl_Message
GROUP BY CAST(date as DATE)
ORDER BY dateDay;

假设每天表中至少有一条记录,这将对您有效。

此问题的正常解决方案是生成所有天数的数据,然后使用
左联接。您可以通过以下几种方式生成天数:

  • 使用日历表
  • 使用递归CTE
  • 使用数字表
  • 在查询中显式地包含日期
在某些情况下,有一种更简单的解决方案,即条件聚合。这假设每天至少有一条记录。然后,您可以为此目的使用条件聚合:

SELECT CAST(date as DATE) as dateDay,
       SUM(CASE WHEN group_id = 1 THEN 1 ELSE 0 END) as countMsgDay
FROM tbl_Message
GROUP BY CAST(date as DATE)
ORDER BY dateDay;

假设每天表中至少有一条记录,这将对您有效。

使用此链接在给定日期之间生成日期。使用开始日期作为
min(dateDay)
和结束日期作为
max(dateDay)

现在使用此表并连接查询。假设要派生表的表是
dateRange
。因此
select*from dateRange
将生成从
2014-10-01
2014-10-03
的日期

现在使用下面的查询来获得所需的输出

select dr.dateval,t.countMsgDay
from dateRange dr
left join
(
    SELECT DATEADD(MINUTE, DATEDIFF(MINUTE, 0, date)/1440 * 1440,0) AS dateDay,
    COUNT(*) AS countMsgDay
    FROM tbl_Message
    WHERE group_id = 1
    GROUP BY DATEADD(MINUTE, DATEDIFF(MINUTE, 0, date)/1440 * 1440,0)
) t
on dr.dateval=t.dateDay

使用此链接可在给定日期之间生成日期。使用开始日期作为
min(dateDay)
和结束日期作为
max(dateDay)

现在使用此表并连接查询。假设要派生表的表是
dateRange
。因此
select*from dateRange
将生成从
2014-10-01
2014-10-03
的日期

现在使用下面的查询来获得所需的输出

select dr.dateval,t.countMsgDay
from dateRange dr
left join
(
    SELECT DATEADD(MINUTE, DATEDIFF(MINUTE, 0, date)/1440 * 1440,0) AS dateDay,
    COUNT(*) AS countMsgDay
    FROM tbl_Message
    WHERE group_id = 1
    GROUP BY DATEADD(MINUTE, DATEDIFF(MINUTE, 0, date)/1440 * 1440,0)
) t
on dr.dateval=t.dateDay

你需要一个日历表,一旦你有了它,你所需要做的就是使用这个表的左连接来获取所有的日期

例:


你需要一个日历表,一旦你有了它,你所需要做的就是使用这个表的左连接来获取所有的日期

例:


您将需要一种方法来生成缺失天数的数据。一个选项是日期表,您可以将其添加到您的模式中。您需要一种方法来为丢失的日期生成数据。一个选项是日期表,您可以将其添加到模式中。