我有一个以前有大量行的空表。
该表有大约 10 个列和其中许多列的索引,以及多个列的索引。
DELETE FROM item WHERE 1=1
这大约需要 40 秒才能完成
SELECT * FROM item
这需要 4 秒。
SELECT * FROM ITEM 的执行计划显示如下;
SQL> select * from midas_item;
no rows selected
Elapsed: 00:00:04.29
Execution Plan
----------------------------------------------------------
0 SELECT STATEMENT Optimizer=CHOOSE (Cost=19 Card=123 Bytes=73
80)
1 0 TABLE ACCESS (FULL) OF 'MIDAS_ITEM' (Cost=19 Card=123 Byte
s=7380)
Statistics
----------------------------------------------------------
0 recursive calls
0 db block gets
5263 consistent gets
5252 physical reads
0 redo size
1030 bytes sent via SQL*Net to client
372 bytes received via SQL*Net from client
1 SQL*Net roundtrips to/from client
0 sorts (memory)
0 sorts (disk)
0 rows processed
知道为什么这些会花费这么长时间以及如何解决它,将不胜感激!
最佳答案
一种可能性是锁。也就是说,表中有一行已被另一个删除提交并锁定。您的删除坐在并等待锁定。提交锁定事务后,您的删除就可以完成了。
第二种可能性是您首先运行了删除,它将块从磁盘提取到缓存中(这需要时间)。 When the select ran, the data was in the cache and so ran quicker.我认为这不太可能,因为您选择的统计数据表明“5252 物理读取”,因此它没有从 SGA 缓存中获取它们。不过,可能涉及磁盘缓存。
第三种可能性是有一个 BEFORE/AFTER DELETE 触发器(不是 FOR EACH ROW)做了一些事情。
第四种可能性是 DELETE 导致延迟块清除。当行被实际删除时,如果它们在提交之前被写入磁盘,它们仍然具有锁定/事务信息。您的删除随之而来,读取块,查看现在过时的事务信息,将其删除并重新写入块。
第五种可能性是争用。也许在删除的同时发生了更多的事情。
很多可能性。如果您可以重现它,则使用等待事件进行跟踪并通过 TKPROF 运行它。
关于sql - 从空表中删除永远,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/2495233/