2017-02-16 189 views
-1

嗨值我有以下日常數據:分組基礎上按日期範圍

daytime  value 
01.01.2017  20000 
02.01.2017  20000 
03.01.2017  20000 
04.01.2017  35000 
05.01.2017  35000 
06.01.2017  40000 
07.01.2017  40000 
08.01.2017  50000 

我怎麼能有日期範圍格式,如下面?

FromDate  ToDate  Value 
01.01.2017 03.01.2017 20000 
04.01.2017 05.01.2017 35000 
06.01.2017 07.01.2017 40000 
08.01.2017 08.01.2017 50000 

謝謝!

回答

3

Tabibitosan處理這個問題很容易:

WITH your_table AS (SELECT to_date('01/01/2017', 'dd/mm/yyyy') daytime, 20000 VALUE FROM dual UNION ALL 
        SELECT to_date('02/01/2017', 'dd/mm/yyyy') daytime, 20000 VALUE FROM dual UNION ALL 
        SELECT to_date('03/01/2017', 'dd/mm/yyyy') daytime, 20000 VALUE FROM dual UNION ALL 
        SELECT to_date('04/01/2017', 'dd/mm/yyyy') daytime, 35000 VALUE FROM dual UNION ALL 
        SELECT to_date('05/01/2017', 'dd/mm/yyyy') daytime, 35000 VALUE FROM dual UNION ALL 
        SELECT to_date('06/01/2017', 'dd/mm/yyyy') daytime, 40000 VALUE FROM dual UNION ALL 
        SELECT to_date('07/01/2017', 'dd/mm/yyyy') daytime, 40000 VALUE FROM dual UNION ALL 
        SELECT to_date('08/01/2017', 'dd/mm/yyyy') daytime, 50000 VALUE FROM dual UNION ALL 
        SELECT to_date('09/01/2017', 'dd/mm/yyyy') daytime, 20000 VALUE FROM dual) 
-- end of mimicking your table with data in it. See SQL below: 
SELECT MIN(daytime) fromdate, 
     MAX(daytime) todate, 
     VALUE 
FROM (SELECT daytime, 
       VALUE, 
       row_number() OVER (ORDER BY daytime) - row_number() OVER (PARTITION BY VALUE ORDER BY daytime) grp 
     FROM your_table) 
GROUP BY grp, 
     VALUE 
ORDER BY MIN(daytime); 

FROMDATE TODATE   VALUE 
---------- ---------- ---------- 
01/01/2017 03/01/2017  20000 
04/01/2017 05/01/2017  35000 
06/01/2017 07/01/2017  40000 
08/01/2017 08/01/2017  50000 
09/01/2017 09/01/2017  20000 

這樣做有什麼比較的行數按日期排序的所有行,然後將行號對於按日期排序的每個值的所有行。如果主數據集中的值行是連續的,那麼兩組數據之間的差異保持不變,因此您可以按此組合。如果存在差距,則差異增加。

在上面的例子中,value = 20000的前三行碰巧是整個集合的前三行,所以差異將是0.但是第四個值= 20000行是整個第九行因此差異現在爲5.您可以很容易地看到,20000的值分爲兩組,因此可以通過在group by子句中包括差異計算來分別找到每個組的最小/最大白天時間。

N.B.這確實假設您的數據中的日期是連續的,或者如果缺少日期,則假定該值在缺失日期保持不變。如果您確實缺少時間,並希望跨不同組顯示差距,則需要將外連接加入包含缺失日期的子查詢中。在這種情況下,我認爲GurV的答案(在評論中提到的案例聲明中的附加條款)將是最好的一個,因爲這樣可以避免將外部連接加入到連續日期列表中。

+0

賓果!有用!非常感謝你:) – akira

+0

不確定你的意思是N.B. - 也許你的意思是,如果頂部有十行,所有值都是20000,但日期是連續四天,那麼一個差距,然後連續六天,這應該產生兩行而不是一行...如果這就是你的意思,然後** Tabibitosan **的小修改可以直接處理。要創建'grp',使用'daytime'本身而不是第一個'row_number()';這樣'grp'值最終會成爲日期而不是數字,但整個事情的工作方式完全相同。 – mathguy

+0

好點,ta;我從來沒有想過要這樣做!星期一將有一個玩弄* {:-) – Boneist

1

如果我理解正確,只要它們對連續日期相同即可。

您可以使用窗口函數根據值生成組,並增加日期順序,然後查找所需的聚合。

with your_table(daytime  ,value) as (
    select to_date('13.02.2017','dd.mm.yyyy'),25000 from dual union all 
    select to_date('14.02.2017','dd.mm.yyyy'),20000 from dual union all 
    select to_date('15.01.2017','dd.mm.yyyy'),90000 from dual union all 
    select to_date('16.01.2017','dd.mm.yyyy'),90000 from dual union all 
    select to_date('17.01.2017','dd.mm.yyyy'),95800 from dual union all 
    select to_date('18.01.2017','dd.mm.yyyy'),95800 from dual union all 
    select to_date('19.01.2017','dd.mm.yyyy'),95800 from dual union all 
    select to_date('20.01.2017','dd.mm.yyyy'),95800 from dual union all 
    select to_date('21.01.2017','dd.mm.yyyy'),95800 from dual union all 
    select to_date('22.01.2017','dd.mm.yyyy'),95800 from dual union all 
    select to_date('23.01.2017','dd.mm.yyyy'),95800 from dual union all 
    select to_date('24.01.2017','dd.mm.yyyy'),90000 from dual union all 
    select to_date('25.01.2017','dd.mm.yyyy'),90000 from dual union all 
    select to_date('26.01.2017','dd.mm.yyyy'),90000 from dual 
) 
select 
    min(daytime) fromdate, 
    max(daytime) todate, 
    value 
from (
    select 
     t.*, 
     sum(x) over (order by daytime) grp 
    from (
     select 
      t.*, 
      case when value = lag(value) over (order by daytime) 
      then 0 else 1 end x 
     from your_table t 
    ) t 
) t group by grp, value 
order by fromdate; 

產地:

FROMDATE TODATE  VALUE 
15-JAN-17 16-JAN-17 90000 
17-JAN-17 23-JAN-17 95800 
24-JAN-17 26-JAN-17 90000 
13-FEB-17 13-FEB-17 25000 
14-FEB-17 14-FEB-17 20000 
+0

嗨,我看到與您的解決方案重複的價值,我會稍後展示示例,謝謝! – akira

+0

@akirax你是什麼意思你看到與GurV的解決方案重複值?看起來它適用於我,當我用一些測試數據嘗試它時。它肯定會給出你輸入數據的輸出結果。 – Boneist

+0

@akirax - 它確實有效。請參閱更新 – GurV