SQL 区间内的聚合和平均值
Aggregation and average value with interval in SQL
我有一个 table 具有这样的数据集
Time_1
Temperature
2020-11-20 12:05:15.520
75
2020-11-20 12:06:50.297
111
2020-11-20 12:08:10.513
147
2020-11-20 12:11:10.593
72
2020-11-20 12:10:46.000
62
2020-11-20 12:15:15.263
171
2020-11-20 12:16:34.577
238
2020-11-20 12:16:45.577
284
2020-11-20 12:18:08.373
304
2020-11-20 12:20:57.030
299
2020-11-20 12:22:21.670
313
2020-11-20 12:34:43.733
100
我想根据另一个时间戳(time_2)的时间间隔(大多数情况下是10分钟间隔)对上述温度数据进行平均,得到类似这样的东西
Time_2
Records_in_interval
Av_Temp
2020-11-20 12:05:19.000
6
106.33
2020-11-20 12:15:19.000
5
287.6
2020-11-20 12:25:19.000
1
100
我面临的一个问题是间隔并不总是 10 分钟。
这是我到目前为止所做的,但它不起作用。
DECLARE @StartDate nvarchar(20)
DECLARE @EndDate nvarchar(20)
SET @StartDate ='2020-11-20 12:00:00'
SET @EndDate = '2020-11-20 23:59:59'
SELECT
[Date1]= CONVERT(datetime, t2.[time_2], 20),
DATEADD(MINUTE, DATEDIFF(MINUTE, t2.[time_2], t1.[time_1]) / 10 * 10,t2.[time_2]) AS [date_truncated],
COUNT(*) AS [records_in_interval],
AVG(t1.[temperature]) AS [Av_Temp]
FROM fix.dbo.main_db2 t2
LEFT JOIN fix1.dbo.main_db1 t1 on DATEADD(MINUTE, DATEDIFF(MINUTE, t2.[time_2], t1.[time_1]) / 10 * 10,t2.[time_2])=t2.[time_2]
WHERE
CONVERT(datetime, t2.[time_2], 20) BETWEEN CONVERT(datetime, @StartDate , 20) AND CONVERT(datetime, @EndDate , 20)
GROUP BY
DATEADD(MINUTE, DATEDIFF(MINUTE, t2.[time_2], t1.[time_1]) / 10 * 10, t2.[time_2]),
t2.[time_2]
ORDER BY
[date_truncated]
如果你有第二个 table 时间,那么你可以使用 join
和聚合:
select t2.time_2, count(temperature), avg(temperature)
from (select t2.*, lead(time_2) over (order by time_2) as next_time_2
from table2 t2
) t2 left join
table1 t1
on t1.time_1 >= t2.time_2 and
t1.time_1 < t2.next_time_2
group by t2.time_2;
编辑:
我认为您可以为此使用相关子查询:
select t2.time_2, count(temperature), avg(temperature)
from (select t2.*,
(select min(tt2.time_2)
from table2 tt2
where tt2.time_2 > t2.time_2
) as next_time_2
from table2 t2
) t2 left join
table1 t1
on t1.time_1 >= t2.time_2 and
t1.time_1 < t2.next_time_2
group by t2.time_2;
但老实说,我不记得 SQL Server 2000 中的限制是什么。在这一点上它完全过时了。
如果您只有第一个 table,您可以使用 union 来获得所有三个结果。
SELECT '2020-11-20 12:05:19.000' AS Time_2,
COUNT(*) AS Records_in_Interval,
AVG(temp) AS Avg_Temp
FROM #temp
WHERE time > '2020-11-20 12:05:19.000' AND time < '2020-11-20 12:15:19.000'
UNION ALL
SELECT '2020-11-20 12:15:19.000' AS Time_2,
COUNT(*) AS Records_in_Interval,
AVG(temp) AS Avg_Temp
FROM #temp
WHERE time > '2020-11-20 12:15:19.000' AND time < '2020-11-20 12:25:19.000'
UNION ALL
SELECT '2020-11-20 12:25:19.000' AS Time_2,
COUNT(*) AS Records_in_Interval,
AVG(temp) AS Avg_Temp
FROM #temp
WHERE time > '2020-11-20 12:25:19.000'
谢谢
我有一个 table 具有这样的数据集
Time_1 | Temperature |
---|---|
2020-11-20 12:05:15.520 | 75 |
2020-11-20 12:06:50.297 | 111 |
2020-11-20 12:08:10.513 | 147 |
2020-11-20 12:11:10.593 | 72 |
2020-11-20 12:10:46.000 | 62 |
2020-11-20 12:15:15.263 | 171 |
2020-11-20 12:16:34.577 | 238 |
2020-11-20 12:16:45.577 | 284 |
2020-11-20 12:18:08.373 | 304 |
2020-11-20 12:20:57.030 | 299 |
2020-11-20 12:22:21.670 | 313 |
2020-11-20 12:34:43.733 | 100 |
我想根据另一个时间戳(time_2)的时间间隔(大多数情况下是10分钟间隔)对上述温度数据进行平均,得到类似这样的东西
Time_2 | Records_in_interval | Av_Temp |
---|---|---|
2020-11-20 12:05:19.000 | 6 | 106.33 |
2020-11-20 12:15:19.000 | 5 | 287.6 |
2020-11-20 12:25:19.000 | 1 | 100 |
我面临的一个问题是间隔并不总是 10 分钟。 这是我到目前为止所做的,但它不起作用。
DECLARE @StartDate nvarchar(20)
DECLARE @EndDate nvarchar(20)
SET @StartDate ='2020-11-20 12:00:00'
SET @EndDate = '2020-11-20 23:59:59'
SELECT
[Date1]= CONVERT(datetime, t2.[time_2], 20),
DATEADD(MINUTE, DATEDIFF(MINUTE, t2.[time_2], t1.[time_1]) / 10 * 10,t2.[time_2]) AS [date_truncated],
COUNT(*) AS [records_in_interval],
AVG(t1.[temperature]) AS [Av_Temp]
FROM fix.dbo.main_db2 t2
LEFT JOIN fix1.dbo.main_db1 t1 on DATEADD(MINUTE, DATEDIFF(MINUTE, t2.[time_2], t1.[time_1]) / 10 * 10,t2.[time_2])=t2.[time_2]
WHERE
CONVERT(datetime, t2.[time_2], 20) BETWEEN CONVERT(datetime, @StartDate , 20) AND CONVERT(datetime, @EndDate , 20)
GROUP BY
DATEADD(MINUTE, DATEDIFF(MINUTE, t2.[time_2], t1.[time_1]) / 10 * 10, t2.[time_2]),
t2.[time_2]
ORDER BY
[date_truncated]
如果你有第二个 table 时间,那么你可以使用 join
和聚合:
select t2.time_2, count(temperature), avg(temperature)
from (select t2.*, lead(time_2) over (order by time_2) as next_time_2
from table2 t2
) t2 left join
table1 t1
on t1.time_1 >= t2.time_2 and
t1.time_1 < t2.next_time_2
group by t2.time_2;
编辑:
我认为您可以为此使用相关子查询:
select t2.time_2, count(temperature), avg(temperature)
from (select t2.*,
(select min(tt2.time_2)
from table2 tt2
where tt2.time_2 > t2.time_2
) as next_time_2
from table2 t2
) t2 left join
table1 t1
on t1.time_1 >= t2.time_2 and
t1.time_1 < t2.next_time_2
group by t2.time_2;
但老实说,我不记得 SQL Server 2000 中的限制是什么。在这一点上它完全过时了。
如果您只有第一个 table,您可以使用 union 来获得所有三个结果。
SELECT '2020-11-20 12:05:19.000' AS Time_2,
COUNT(*) AS Records_in_Interval,
AVG(temp) AS Avg_Temp
FROM #temp
WHERE time > '2020-11-20 12:05:19.000' AND time < '2020-11-20 12:15:19.000'
UNION ALL
SELECT '2020-11-20 12:15:19.000' AS Time_2,
COUNT(*) AS Records_in_Interval,
AVG(temp) AS Avg_Temp
FROM #temp
WHERE time > '2020-11-20 12:15:19.000' AND time < '2020-11-20 12:25:19.000'
UNION ALL
SELECT '2020-11-20 12:25:19.000' AS Time_2,
COUNT(*) AS Records_in_Interval,
AVG(temp) AS Avg_Temp
FROM #temp
WHERE time > '2020-11-20 12:25:19.000'
谢谢