currently we have a working query that selects from a large partitioned table for processing. The table is partitioned by daily range, with 1 day of data in 1 partition.
The query is:
SELECT /*+parallel(auto)*/ a.*
FROM TBL_EXCLUDED a
WHERE (not exists(
select 1 from C_HISTORY history
inner join C_MATRIX_EXT ext on ext.from_type = (CASE WHEN UPPER(history.TYPE_CD)<>'B' THEN 'C' ELSE 'B' END) and ext.from_channel = history.channel
where history.mid= a.mid
and ext.to_channel = a.channel and ext.to_type = (CASE WHEN UPPER(a.TYPE_CD)<>'B' THEN 'C' ELSE 'B' END)
and history.channel_sent_dt>=TRUNC (SYSDATE-ext.duration+1)
and history.channel_sent_dt<=TRUNC (SYSDATE)+1
) )
The explain plan is a bit long so i'll only show the part with the partition. Note that the PARTITION_START
is 1
and PARTITION_STOP
is KEY
Now if i change the criteria to search from a fixed date, rather than deriving it from sysdate
, the cost will change:
SELECT /*+parallel(auto)*/ a.*
FROM TBL_EXCLUDED a
WHERE (not exists(
select 1 from C_HISTORY history
inner join C_MATRIX_EXT ext on ext.from_type = (CASE WHEN UPPER(history.TYPE_CD)<>'B' THEN 'C' ELSE 'B' END) and ext.from_channel = history.channel
where history.mid= a.mid
and ext.to_channel = a.channel and ext.to_type = (CASE WHEN UPPER(a.TYPE_CD)<>'B' THEN 'C' ELSE 'B' END)
and history.channel_sent_dt>=TRUNC ( TO_DATE('10-09-2015','dd-mm-yy') )
and history.channel_sent_dt<=TRUNC ( TO_DATE('17-09-2015','dd-mm-yy') )+1
) )
The explain now showing far lesser cost:
Will the actual execution differs from this plan? Also, although in the query with sysdate
the cost is high, will the actual execution be far lesser since it should be able to select from the targeted partitions only?
And finally, will there be actual benefit in using the 2nd way of querying on range partitioned table rather than the 1st query?
Appreciate all the response and guidance, thank you.