以下是我自己的做法:
我创建了一个包含一些值的表格,如:
CREATE TABLE my_test AS
SELECT ROWNUM ID, TRUNC(SYSDATE)+(LEVEL*5/24/60/60)date_time , 111 person_id
FROM dual CONNECT BY LEVEL <= (24*60*60)/5
ORDER BY 1;
现在,我在person_id = 222
和date_time
5:30 am
的表格6:30 am
UPDATE my_test
SET person_id = 222
WHERE date_time >= trunc(SYSDATE)+ 5/24 + 30/24/60
AND DATE_TIME <= trunc(sysdate)+ 6/24 + 30/24/60;
我需要记录每小时的人数,所以我写了一个代码:
SELECT time_range,count(distinct person_id) PERSON_COUNT
FROM (
select person_id , date_time,
case TO_CHAR(date_time,'hh24') when '00' then '12 AM - 01 AM'
when '01' then '01 AM - 02 AM'
when '02' then '02 AM - 03 AM'
when '03' then '03 AM - 04 AM'
when '04' then '04 AM - 05 AM'
when '05' then '05 AM - 06 AM'
when '06' then '06 AM - 07 AM'
when '07' then '07 AM - 08 AM'
when '08' then '08 AM - 09 AM'
when '09' then '09 AM - 10 AM'
when '10' then '10 AM - 11 AM'
when '11' then '11 AM - 12 PM'
when '12' then '12 PM - 01 PM'
when '13' then '01 PM - 02 PM'
when '14' then '02 PM - 03 PM'
when '15' then '03 PM - 04 PM'
when '16' then '04 PM - 05 PM'
when '17' then '05 PM - 06 PM'
when '18' then '06 PM - 07 PM'
when '19' then '07 PM - 08 PM'
when '20' then '08 PM - 09 PM'
when '21' then '09 PM - 10 PM'
when '22' then '10 PM - 11 PM'
WHEN '23' THEN '11 PM - 12 AM' end time_range
FROM my_test
WHERE date_time >= trunc(SYSDATE)
AND date_time < trunc(SYSDATE)+1
ORDER BY date_time)
GROUP BY time_range;
它的工作正常,没有预期的订购。 (time_range的顺序没有给出预期,因为它是外部查询中的字符串)。
我需要按time_range订购,并且对上述任何简单易用的代码表示赞赏。 提前谢谢。
答案 0 :(得分:2)
ORDER BY
子句始终是在单个查询中解释的最后一个子句,但是它在子查询中,因此主查询GROUP BY
将“覆盖”您的ORDER BY
。< / p>
你可以写一下:
SELECT time_range, COUNT(DISTINCT person_id) PERSON_COUNT
FROM (SELECT person_id,
date_time,
CASE TO_CHAR(date_time, 'hh24')
WHEN '00' THEN
'12 AM - 01 AM'
/*[snip]*/
WHEN '23' THEN
'11 PM - 12 AM'
END time_range
FROM my_test
WHERE date_time >= trunc(SYSDATE)
AND date_time < trunc(SYSDATE) + 1)
GROUP BY time_range, TO_CHAR(date_time, 'hh24')
ORDER BY TO_CHAR(date_time, 'hh24');
此外,我不是你time_range
表达的粉丝。您可以将其重写为:
to_char(date_time, 'HH PM - ') || to_char(date_time + 1/24, 'HH PM') time_range
编辑:显然你需要完整的查询:
SELECT time_range, COUNT(DISTINCT person_id) PERSON_COUNT
FROM (SELECT person_id,
date_time,
to_char(date_time, 'HH PM - ')
|| to_char(date_time + 1/24, 'HH PM') time_range
FROM my_test
WHERE date_time >= trunc(SYSDATE)
AND date_time < trunc(SYSDATE) + 1)
GROUP BY time_range, TO_CHAR(date_time, 'hh24')
ORDER BY TO_CHAR(date_time, 'hh24');
答案 1 :(得分:1)
首先,您应该在外部查询中使用order by
而不是内部查询。内部查询中的order by
通常不能保证有效。
但是,即使你把:
order by date_time;
最后,你仍然无法得到你想要的东西。为此,请尝试按date_time
本身排序,如:
order by max(date_time);
以下是子查询中order by
{{1}}的示例:
ORDER BY子句允许您指定行的顺序 出现在结果集中。在子查询中,ORDER BY子句是 没有意义,除非它伴随着一个或两个结果 offset和fetch first子句或与ROW_NUMBER一起使用 功能,因为无法保证订单保留在 外部结果集。允许将ORDER BY组合在一起 在子查询中使用ORDER BY进行外部查询。
答案 2 :(得分:0)
select case TO_CHAR(date_time,'hh24') when '00' then '12 AM - 01 AM'
when '01' then '01 AM - 02 AM'
when '02' then '02 AM - 03 AM'
when '03' then '03 AM - 04 AM'
when '04' then '04 AM - 05 AM'
when '05' then '05 AM - 06 AM'
when '06' then '06 AM - 07 AM'
when '07' then '07 AM - 08 AM'
when '08' then '08 AM - 09 AM'
when '09' then '09 AM - 10 AM'
when '10' then '10 AM - 11 AM'
when '11' then '11 AM - 12 PM'
when '12' then '12 PM - 01 PM'
when '13' then '01 PM - 02 PM'
when '14' then '02 PM - 03 PM'
when '15' then '03 PM - 04 PM'
when '16' then '04 PM - 05 PM'
when '17' then '05 PM - 06 PM'
when '18' then '06 PM - 07 PM'
when '19' then '07 PM - 08 PM'
when '20' then '08 PM - 09 PM'
when '21' then '09 PM - 10 PM'
when '22' then '10 PM - 11 PM'
WHEN '23' THEN '11 PM - 12 AM' end time_range,
count(person_id) person_count
FROM my_test
WHERE date_time >= trunc(SYSDATE)
AND date_time < trunc(SYSDATE)+1
group by TO_CHAR(date_time,'hh24')
ORDER BY 1