2017-08-29 117 views
0

我有一个表,如下组数据按时间间隔

order no  orderdate 
01    2012-08-01 00:00 
02    2012-08-01 00:10 
03    2012-08-01 00:15 
04    2012-08-01 00:30 
05    2012-08-01 10:00 
06    2012-08-01 10:35 
07    2012-08-01 14:00 
08    2012-08-02 20:30 
09    2012-08-02 20:35 
10    2012-08-02 23:00 

我通过时间间隔(如00 -01,01- 02 ...... 22- 23要组此值,23-24)(不包括日期值)

如何编写查询以按时间对其进行分组?

我希望得到24行(24个间隔)与订单

+0

可以'组时CONDITION1 THEN 1 BY CASE WHEN 2 THEN ... CONDITION2'。 – RealCheeseLord

+0

'我想获得24行(24间隔)的订单数'!!,你能否以表格格式提供我们想要的输出? –

回答

1

您可以使用GROUP BY DATEPART(HOUR, orderdate)

查询:

SELECT DATEPART(HOUR, orderdate) AS HOUR, 
     COUNT(*)     AS ORDERS_PER_HOUR 
FROM YourTable 
WHERE CAST(orderdate AS DATE) = @someDate 
GROUP BY DATEPART(HOUR, orderdate) 

注意,上面的查询将给予不超过24分的结果,如果不是每一个小时出现在orderdate

如果需要已经代表了所有时间,那么你可以使用一个递归公用表表达式(CTE)首先生成所有的小时(0-23),然后只剩下CTE加入你的表:

;WITH hours AS 
(
    SELECT 0 AS h 
    UNION ALL 
    SELECT h + 1 FROM hours WHERE h < 23 
) 
SELECT hours.h AS HOUR, 
     COUNT(YourTable.[order no]) AS ORDERS_PER_HOUR 
FROM  hours 
LEFT JOIN YourTable ON DATEPART(HOUR, orderdate) = hours.h 
WHERE CAST(orderdate AS DATE) = @someDate 
GROUP BY hours.h 
0

的数量在这里您区分一天的时间一个简单的解决方案...

drop table if exists dbo.tOrders; 

create table dbo.tOrders (
    OrderNo varchar(50) 
    , OrderDate datetime 
); 

insert into dbo.tOrders (OrderNo, OrderDate) 
values ('01', '2012-08-01 00:00') 
    , ('02', '2012-08-01 00:10') 
, ('03',    '2012-08-01 00:15') 
, ('04',    '2012-08-01 00:30') 
, ('05',    '2012-08-01 10:00') 
, ('06',    '2012-08-01 10:35') 
, ('07',    '2012-08-01 14:00') 
, ('08',    '2012-08-02 20:30') 
, ('09',    '2012-08-02 20:35') 
, ('10',    '2012-08-02 23:00') 



select 
    case 
     when datepart(hour, t.OrderDate) >= 0 and datepart(hour, t.OrderDate) < 1 then '00-01' 
     when datepart(hour, t.OrderDate) >= 1 and datepart(hour, t.OrderDate) < 2 then '01-02' 
     when datepart(hour, t.OrderDate) >= 2 and datepart(hour, t.OrderDate) < 3 then '02-03' 
     when datepart(hour, t.OrderDate) >= 3 and datepart(hour, t.OrderDate) < 4 then '03-04' 
     when datepart(hour, t.OrderDate) >= 4 and datepart(hour, t.OrderDate) < 5 then '04-05' 
     when datepart(hour, t.OrderDate) >= 5 and datepart(hour, t.OrderDate) < 6 then '05-06' 
     when datepart(hour, t.OrderDate) >= 6 and datepart(hour, t.OrderDate) < 7 then '06-07' 
     when datepart(hour, t.OrderDate) >= 7 and datepart(hour, t.OrderDate) < 8 then '07-08' 
     when datepart(hour, t.OrderDate) >= 8 and datepart(hour, t.OrderDate) < 9 then '08-09' 
     when datepart(hour, t.OrderDate) >= 9 and datepart(hour, t.OrderDate) < 10 then '09-10' 
     when datepart(hour, t.OrderDate) >= 10 and datepart(hour, t.OrderDate) < 11 then '10-11' 
     when datepart(hour, t.OrderDate) >= 11 and datepart(hour, t.OrderDate) < 12 then '11-12' 
     when datepart(hour, t.OrderDate) >= 12 and datepart(hour, t.OrderDate) < 13 then '12-13' 
     when datepart(hour, t.OrderDate) >= 13 and datepart(hour, t.OrderDate) < 14 then '13-14' 
     when datepart(hour, t.OrderDate) >= 14 and datepart(hour, t.OrderDate) < 15 then '14-15' 
     when datepart(hour, t.OrderDate) >= 15 and datepart(hour, t.OrderDate) < 16 then '15-16' 
     when datepart(hour, t.OrderDate) >= 16 and datepart(hour, t.OrderDate) < 17 then '16-17' 
     when datepart(hour, t.OrderDate) >= 17 and datepart(hour, t.OrderDate) < 18 then '17-18' 
     when datepart(hour, t.OrderDate) >= 18 and datepart(hour, t.OrderDate) < 19 then '18-19' 
     when datepart(hour, t.OrderDate) >= 19 and datepart(hour, t.OrderDate) < 20 then '19-20' 
     when datepart(hour, t.OrderDate) >= 20 and datepart(hour, t.OrderDate) < 21 then '20-21' 
     when datepart(hour, t.OrderDate) >= 21 and datepart(hour, t.OrderDate) < 22 then '21-22' 
     when datepart(hour, t.OrderDate) >= 22 and datepart(hour, t.OrderDate) < 23 then '22-23' 
     when datepart(hour, t.OrderDate) >= 23 then '23-00' 
    end as TimeOfDay 
    , count(t.OrderNo) as OrderCount 
from dbo.tOrders t 
group by 
    case 
     when datepart(hour, t.OrderDate) >= 0 and datepart(hour, t.OrderDate) < 1 then '00-01' 
     when datepart(hour, t.OrderDate) >= 1 and datepart(hour, t.OrderDate) < 2 then '01-02' 
     when datepart(hour, t.OrderDate) >= 2 and datepart(hour, t.OrderDate) < 3 then '02-03' 
     when datepart(hour, t.OrderDate) >= 3 and datepart(hour, t.OrderDate) < 4 then '03-04' 
     when datepart(hour, t.OrderDate) >= 4 and datepart(hour, t.OrderDate) < 5 then '04-05' 
     when datepart(hour, t.OrderDate) >= 5 and datepart(hour, t.OrderDate) < 6 then '05-06' 
     when datepart(hour, t.OrderDate) >= 6 and datepart(hour, t.OrderDate) < 7 then '06-07' 
     when datepart(hour, t.OrderDate) >= 7 and datepart(hour, t.OrderDate) < 8 then '07-08' 
     when datepart(hour, t.OrderDate) >= 8 and datepart(hour, t.OrderDate) < 9 then '08-09' 
     when datepart(hour, t.OrderDate) >= 9 and datepart(hour, t.OrderDate) < 10 then '09-10' 
     when datepart(hour, t.OrderDate) >= 10 and datepart(hour, t.OrderDate) < 11 then '10-11' 
     when datepart(hour, t.OrderDate) >= 11 and datepart(hour, t.OrderDate) < 12 then '11-12' 
     when datepart(hour, t.OrderDate) >= 12 and datepart(hour, t.OrderDate) < 13 then '12-13' 
     when datepart(hour, t.OrderDate) >= 13 and datepart(hour, t.OrderDate) < 14 then '13-14' 
     when datepart(hour, t.OrderDate) >= 14 and datepart(hour, t.OrderDate) < 15 then '14-15' 
     when datepart(hour, t.OrderDate) >= 15 and datepart(hour, t.OrderDate) < 16 then '15-16' 
     when datepart(hour, t.OrderDate) >= 16 and datepart(hour, t.OrderDate) < 17 then '16-17' 
     when datepart(hour, t.OrderDate) >= 17 and datepart(hour, t.OrderDate) < 18 then '17-18' 
     when datepart(hour, t.OrderDate) >= 18 and datepart(hour, t.OrderDate) < 19 then '18-19' 
     when datepart(hour, t.OrderDate) >= 19 and datepart(hour, t.OrderDate) < 20 then '19-20' 
     when datepart(hour, t.OrderDate) >= 20 and datepart(hour, t.OrderDate) < 21 then '20-21' 
     when datepart(hour, t.OrderDate) >= 21 and datepart(hour, t.OrderDate) < 22 then '21-22' 
     when datepart(hour, t.OrderDate) >= 22 and datepart(hour, t.OrderDate) < 23 then '22-23' 
     when datepart(hour, t.OrderDate) >= 23 then '23-00' 
    end 
0

我想你可以使用这个查询。正如您所看到的,主要使用的函数是DATE_PART(<format>, <date column>)(请参阅https://docs.microsoft.com/en-us/sql/t-sql/functions/datepart-transact-sql),其中“返回表示指定日期的指定日期部分的整数”。

然后你可以使用GROUP BY来COUNT记录每个小时。

最后你可以安排“输出格式”。

SELECT CAST(X AS VARCHAR(2)) +'-'+CAST(X+1 AS VARCHAR(2)) AS HOUR_GROUP, COUNT(*) AS RC 
FROM 
(SELECT DATEPART(hh,ORD_DATE) X FROM ORD)A 
GROUP BY X 
; 

或者如果你喜欢:

SELECT CAST(DATEPART(hh,ORD_DATE) AS VARCHAR(2)) +'-'+CAST(DATEPART(hh,ORD_DATE) +1 AS VARCHAR(2)) AS HOUR_GROUP, COUNT(*) AS RC 
FROM ORD 
GROUP BY DATEPART(hh,ORD_DATE) 
; 

的样本数据:

INSERT INTO ORD VALUES (1,'2012-01-08 00:00'); 
INSERT INTO ORD VALUES (2,'2012-01-08 00:10'); 
INSERT INTO ORD VALUES (3,'2012-01-08 00:15'); 
INSERT INTO ORD VALUES (4,'2012-01-08 00:30'); 
INSERT INTO ORD VALUES (9,'2012-01-08 01:30'); 
INSERT INTO ORD VALUES (5,'2012-01-08 10:00'); 
INSERT INTO ORD VALUES(7,'2012-01-08 15:00'); 
INSERT INTO ORD VALUES (8,'2012-02-08 20:30'); 

输出

HOUR_GROUP RC 
0-1  4 
1-2  1 
10-11 1 
15-16 1 
20-21 1 

如果你希望你可以使用所有的24小时组:

SELECT RIGHT('0'+CAST(Z AS VARCHAR(2)),2)+'-'+RIGHT('0'+CAST(Z+1 AS VARCHAR(2)),2) AS HOUR_GR, COALESCE(RC,0) AS RC 
FROM (
    SELECT -1+ROW_NUMBER() OVER (ORDER BY A1.Y) AS Z 
    FROM (SELECT 1 AS Y UNION ALL SELECT 2 UNION ALL SELECT 3 UNION ALL SELECT 4 UNION ALL SELECT 5) A1 
      CROSS JOIN (SELECT 1 AS Y UNION ALL SELECT 2 UNION ALL SELECT 3 UNION ALL SELECT 4 UNION ALL SELECT 5) A2 
    ) B 
LEFT JOIN (SELECT X, CAST(X AS VARCHAR(2)) +'-'+CAST(X +1 AS VARCHAR(2)) AS HOUR_GROUP, COUNT(*) AS RC 
      FROM (SELECT DATEPART(hh,ORD_DATE) X FROM ORD) A 
      GROUP BY X 
      ) C ON B.Z= C.X 
WHERE B.Z<24 

输出:

HOUR_GR RC 
00-01 4 
01-02 1 
02-03 0 
03-04 0 
04-05 0 
05-06 0 
06-07 0 
07-08 0 
08-09 0 
09-10 0 
10-11 1 
11-12 0 
12-13 0 
13-14 0 
14-15 0 
15-16 1 
16-17 0 
17-18 0 
18-19 0 
19-20 0 
20-21 1 
21-22 0 
22-23 0 
23-24 0 
0

如果我理解正确的话,你是按小时考虑日期寻找数,即你正在努力寻找一天中最繁忙的时刻?在这种情况下,你可以使用以下命令:

declare @hours table 
(
hourpart datetime 
) 
INSERT INTO @hours VALUES 
('00:00:00'), 
('01:00:00'), 
('02:00:00'), 
('03:00:00'), 
('04:00:00'), 
('05:00:00'), 
('06:00:00'), 
('07:00:00'), 
('08:00:00'), 
('09:00:00'), 
('10:00:00'), 
('11:00:00'), 
('12:00:00'), 
('13:00:00'), 
('14:00:00'), 
('15:00:00'), 
('16:00:00'), 
('17:00:00'), 
('18:00:00'), 
('19:00:00'), 
('20:00:00'), 
('21:00:00'), 
('22:00:00'), 
('23:00:00') 

declare @orders table 
(
orderNo int, 
orderDate datetime) 


INSERT INTO @orders VALUES 
(01,'2012-08-01 00:00'), 
(02,'2012-08-01 00:10'), 
(03,'2012-08-01 00:15'), 
(04,'2012-08-01 00:30'), 
(05,'2012-08-01 10:00'), 
(06,'2012-08-01 10:35'), 
(07,'2012-08-01 14:00'), 
(08,'2012-08-02 20:30'), 
(09,'2012-08-02 20:35'), 
(10,'2012-08-02 23:00'), 
(11,'2012-08-01 20:25') 

SELECT convert(varchar(8), h.hourpart, 108), COUNT(*) FROM @orders o 
INNER JOIN @hours h 
ON DATEPART(hour, o.orderdate) = DATEPART(hour, h.hourpart) 
GROUP BY h.hourpart 
ORDER BY h.hourpart 

结果:

00:00:00 4 
10:00:00 2 
14:00:00 1 
20:00:00 3 
23:00:00 1