我有两个具有以下结构的表
INPUTFILELOG ,列为
FILE_ID
RECORD_SEQ
ACCOUNT
CHILD_ACCOUNT
清除,列为
ACCOUNT
DATE
DETAILS
查询
delete from INPUTFILELOG il
where exists
( select 1 from PURGE po
where po.account = ':NUMBER'
and ( po.account = il.account OR po.account = il.child_account ) )
即使在 PURGE.ACCOUNT 和 INPUTFILELOG.ACCOUNT 和 INPUTFILELOG.CHILD_ACCOUNT 上都有索引,上述查询的性能也很差。有人可以吗 请帮忙吗?
更新
我尝试了以下查询。看起来不错吗?有没有更好的方法来处理它?</ p>
delete from INPUTLOG sif
where exists
( select t.fileno, t.rec
from ( SELECT sif2.FILE_ID as fileno, sif2.RECORD_SEQ as rec
FROM purge po
INNER JOIN INPUTLOG sif2
ON ( po.ACCOUNT = sif2.ACCOUNT
OR po.ACCOUNT = sif2.CHILD_ACCOUNT )
where po.account = ':NUMBER' ) t
WHERE sif.FILE_ID = t.FILEno
AND sif.record_seq = t.rec)
答案 0 :(得分:1)
根据您的最新输入,我建议将原始查询分为以下两个查询,并验证它们在功能上是否正常(我认为应该如此)并验证其性能。我认为以下两个方法可能会更好,而这里的问题可能是由于“ OR OPERATOR”导致了全表扫描。
DELETE FROM INPUTLOG il
WHERE EXISTS
(SELECT 1
FROM PURGE po
WHERE po.account = ':NUMBER' AND (po.account = il.account))
DELETE FROM INPUTLOG il
WHERE EXISTS
(SELECT 1
FROM PURGE po
WHERE po.account = ':NUMBER'
AND (po.account = il.child_account))
答案 1 :(得分:0)
您只想删除一个帐户。如果表中只有10个帐户,则全表扫描将是删除很大一部分表数据的最佳方法。但是您说,当您只删除帐户或子帐户时,删除要快得多。我认为这两次删除的总和时间比合并查询的总和要短得多。因此显然可以使用索引,这意味着它只能是要删除的表的很小一部分。
两个想法:
INPUTFILELOG
(由inputfilelog.account = ...
删除)中删除的一个帐户。因此:
delete from inputfilelog where account =
(select account from purge where account = ':NUMBER');
delete from inputfilelog where child_account =
(select account from purge where account = ':NUMBER');
也许=
甚至足以使组合的statemet快速运行(但通常不能将两个索引与OR
组合使用)。
delete from inputfilelog
where account = (select account from purge where account = ':NUMBER')
or child_account = (select account from purge where account = ':NUMBER');
使用inputfilelog.account = ...
的另一种方法:
delete from inputfilelog
where (account = :NUMBER or child_account = :NUMBER)
and exists (select * from purge where account = :NUMBER);