通过对一天的值求和,我的查询完全正常。
SELECT CAST(fldDateTime AS DATE) AS DayValue, SUM(fldValue) AS Val
FROM [dbo].[Data.tblMeterData]
GROUP BY CAST(fldDateTime AS DATE)
ORDER BY DayValue
我遇到的问题是我需要将数据大于午夜并持续到第二天的午夜。为了测试我可以做到这一点,我测试了以下代码,这有助于我处理没有一整天的第一批值。
DECLARE @a DATETIME
DECLARE @b DATETIME
SET @a = CAST('2016-03-21 00:01:00' AS DATETIME)
SET @b = DATEADD(SECOND,-86399 ,@a)
SELECT @a AS a, @b AS b
SELECT CAST(fldDateTime AS DATE) AS DayValue, SUM(fldValue) AS Val
FROM [dbo].[Data.tblMeterData]
WHERE fldDateTime BETWEEN @b AND @a
GROUP BY CAST(fldDateTime AS DATE)
ORDER BY DayValue
这个问题是我不想循环浏览日期,因为我有成千上万的ID需要以这种方式处理。我不能包括第一个日期的午夜,因为第一个数据是在午夜之后录制,最后的每日阅读时间是第二天的午夜,例如
Date > '2016-03-20 00:00:00' AND <= 2016-03-21 00:00:00
如何执行以下操作:
答案 0 :(得分:1)
我对要求的理解是,您正在寻找按度计ID和日期计算的值组的总和,但是对于每个日期,我们还希望包含第二天的值。这意味着每个值将计入当天和前一天的总和。
代码:
--generate test data
declare @tblMeterData table (
[ID] [int] IDENTITY(1,1) NOT NULL,
[tblMeterData_Id] [int] NOT NULL,
[fldDateTime] [datetime] NOT NULL,
[fldValue] [decimal](18, 2) NULL,
[fldBatchId] [uniqueidentifier] NOT NULL);
insert @tblMeterData (tblMeterData_Id, fldDateTime, fldValue, fldBatchId) values
(18, '2016-12-19 23:59:59', 1.0, newid()),
(18, '2016-12-20 00:00:00', 2.0, newid()),
(18, '2016-12-20 00:30:00', 3.0, newid()),
(18, '2016-12-20 01:00:00', 4.0, newid()),
(18, '2016-12-20 01:30:00', 5.0, newid()),
(18, '2016-12-21 00:00:00', 6.0, newid()),
(18, '2016-12-21 00:30:00', 7.0, newid()),
(18, '2016-12-22 00:00:00', 8.0, newid()),
(18, '2016-12-23 00:00:00', 9.0, newid()),
(19, '2016-12-20 00:00:00', 10.0, newid());
--select * from @tblMeterData order by ID;
--main query
with cte as (
--0:00:00 reports on previous day
select *, cast(dateadd(S, -1, fldDateTime) as date) group_date
from @tblMeterData
union all
--duplicate all records to also group on previous day
select *, cast(dateadd(D, -1, dateadd(S, -1, fldDateTime)) as date) group_date
from @tblMeterData
)
select tblMeterData_Id, group_date, sum(fldValue) sum_value
from cte
group by tblMeterData_Id, group_date
order by tblMeterData_Id, group_date;
结果:
tblMeterData_Id group_date sum_value
18 2016-12-18 3.00
18 2016-12-19 21.00
18 2016-12-20 33.00
18 2016-12-21 24.00
18 2016-12-22 9.00
19 2016-12-18 10.00
19 2016-12-19 10.00
答案 1 :(得分:1)
答案如下:
WITH cte AS (
SELECT *, CAST(DATEADD(S, -1, fldDateTime) AS DATE) group_date
FROM [dbo].[Data.tblMeterData]
)
SELECT tblMeterData_Id, group_date, SUM(fldValue) sum_value
FROM cte
GROUP BY tblMeterData_Id, group_date
ORDER BY tblMeterData_Id, group_date;
效果很好。