【问题标题】:Using VARRAYs to overlap time series data使用 VARRAY 重叠时间序列数据
【发布时间】:2017-11-14 16:51:30
【问题描述】:

我有一些数据想要重叠,如下所示。可能还有一些更聪明的方法,因为数据很大,请指教。

这是我的 VArray:

CREATE OR REPLACE TYPE NUMBER_VARRAY_5 AS VARRAY (5) OF NUMBER NOT NULL

这是原始数据(表 TEST_1)

"DATE_A","TOTO3_A"
"01/01/2005","281.25"
"02/01/2005","-9999.00"
"03/01/2005","291.50"
"04/01/2005","310.50"
"05/01/2005","298.75"
"06/01/2005","300.75"

表 TEST_2 是按日期滞后 1 天和固定天数(5 天)重叠的结果

"DATE_START","DATE_END","O3"
"01/01/2005","05/01/2005","<Collection>"
1      281.25
2      -9999
3      291.5
4      310.5
5      298.75
"02/01/2005","06/01/2005","<Collection>"
1      -9999
2      291.5
3      310.5
4      298.75
5      300.75

这是我的代码

CREATE OR REPLACE PROCEDURE TEST
IS
   NUMBER_VARRAY   NUMBER_VARRAY_5 := NUMBER_VARRAY_5 ();
   L_VALUE         NUMBER;
   MIN_DATE        DATE;
   MAX_DATE        DATE;

BEGIN
   SELECT MIN (DATE_A), MAX (DATE_A)
     INTO MIN_DATE, MAX_DATE
     FROM TEST_1;

   FOR CUR_R IN 0 .. (MAX_DATE - MIN_DATE - 4)       
   LOOP
      L_VALUE := 0;

      FOR I IN CUR_R .. (CUR_R + 4)
      LOOP
         L_VALUE := L_VALUE + 1;
         NUMBER_VARRAY.EXTEND;

         SELECT TOTO3_A
           INTO NUMBER_VARRAY (L_VALUE)
           FROM TEST_1
          WHERE DATE_A = MIN_DATE + I;
      END LOOP;

      INSERT INTO TEST_2 (DATE_START, DATE_END, O3)
           VALUES (MIN_DATE + CUR_R, (MIN_DATE + CUR_R + 4), NUMBER_VARRAY);

      COMMIT;

      NUMBER_VARRAY.DELETE ();
   END LOOP;
END TEST;

【问题讨论】:

    标签: sql oracle performance user-defined-types


    【解决方案1】:

    我认为您可以使用 COLLECT 函数在纯 SQL 中执行此操作:

    with dt as ( select max(date_a)-4 as mx from TEST_1 )
       , dr as ( select date_a as date_start
                        , date_a + 4 as date_end 
                from TEST_1 
                     cross join dt
                 where date_a <= dt.mx )
    select dr.*
           , cast(collect(TEST_1.toto3_a) as NUMBER_VARRAY_5) as coll03
    from TEST_1
          cross join dr
    where TEST_1.date_a between dr.date_start and dr.date_end  
    group by dr.date_start, dr.date_end
    order by dr.date_start
    /
    

    " 有一些错误:ORA-22814: 属性或元素值大于类型中指定的值"

    嗯,试试这个巫毒:

     cast(collect(cast(TEST_1.toto3_a as number)) as NUMBER_VARRAY_5)
    

    【讨论】:

    • 您好,有一些错误:ORA-22814: 属性或元素值大于类型中指定的值
    • 创建或替换类型 NUMBER_VARRAY_5 作为 VARRAY (5) OF NUMBER NOT NULL;
    • 对了,谢谢,ORDER BY 1 这里的“1”是什么意思?
    • 这只是一种说“按投影的第一列排序”而不实际输入列名的方式。如果此答案有用,请投票和/或接受它。接受的答案提高了 StackOverflow 作为其他 Seeker 资源的质量
    猜你喜欢
    • 2021-09-19
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2016-10-27
    • 2014-06-03
    • 2012-01-29
    • 2017-11-28
    • 2022-06-19
    相关资源
    最近更新 更多