ORACLE SQL - 比较没有连接的日期

时间:2017-07-14 14:10:50

标签: sql oracle

我有一个非常大的数据表,超过10亿行。如果我尝试将该表连接到自己进行比较,则估计计划的成本是不可挽回的(成本:226831405289150)。有没有一种方法可以在没有连接的情况下实现与下面的查询相同的结果,也许是过度分区?

我需要做的是确保在收到野生护理的那个之前或之后的24小时内没有发生另一个事件。

非常感谢你的帮助!

select e2.SYSTEM_NO,
       min(e2.DT) as dt
from   SYSTEM_EVENT e2
       inner join table1.event el2
       on el2.event_id = e2.event_id 
       left join ( Select se.DT
                   from  SYSTEM_EVENT se
                   where
                         --fails
                         (   se.event_id in ('101','102','103','104')
                         --restores
                          or se.event_id in ('106','107','108','109')
                         )
                  ) e3
       on e3.dt-e2.dt between .0001 and 1
       or e3.dt-e2.dt between -1 and .0001
where  el2.descr like '%WILDCARE%'
and    e3.dt is null
and    e2.REC_STS_CD = 'A'
group by e2.SYSTEM_NO  

2 个答案:

答案 0 :(得分:1)

没有任何测试数据很难确定您要实现的目标,但似乎您可以尝试使用带范围窗口的分析函数:

SELECT system_no,
       MIN( dt ) AS dt
FROM   (
  SELECT system_no,
         dt,
         COUNT(
           CASE
           WHEN (  se.event_id in ('101','102','103','104')   --fails
                OR se.event_id in ('106','107','108','109') ) --restores
           THEN 1
           END
         ) OVER (
           ORDER BY dt
           RANGE BETWEEN 1 PRECEDING AND 1 FOLLOWING
         ) AS num
  FROM   system_event
) se
WHERE  num = 0
AND    REC_STS_CD = 'A'
AND    EXISTS(
  SELECT 1
  FROM   table1.event te
  WHERE  te.descr like '%WILDCARE%'
  AND    te.event_id = se.event_id
)
GROUP BY system_no

答案 1 :(得分:1)

这不是您问题的直接答案,但评论时间太长了。

可以插入多少旧数据? 48h窗口意味着如果数据以递增方式插入,则只需要检查数据的子集而不是整个1bilion行表。因此,如果是,请通过某些with子句或temporary table来比较数据。

如果您还需要在整个表格中进行比较,我会按event_id或其他属性进行分区,如果有更好的分区。并分别比较每个组。

where el2.descr like '%WILDCARE%'是这种巨大表格的性能杀手。