我的oracle数据库中的更新语句有问题。 查询需要花费很多时间,临时表空间空间不足,但它提供了正确的数据。
我尝试将子查询转换为连接,但我无法弄清楚如何正确地执行此操作。 如果有人知道如何改进声明或如何将其转换为连接,我将非常感激。
UPDATE table1 t1
SET t1.inxdc = (SELECT sda_x
FROM table2 t2
WHERE t1.c1 = t2.c1
AND t1.c2 = t2.c2
AND t1.c3 = t2.c3
AND t1.c4 = t2.c4
AND t1.c5 = t2.c5
AND t1.c6 = t2.c6
AND t2.ident = 'K_SDA_W'
AND rownum=1)
WHERE EXISTS
(SELECT 1
FROM table2 t2
WHERE t1.c1 = t2.c1
AND t1.c2 = t2.c2
AND t1.c3 = t2.c3
AND t1.c4 = t2.c4
AND t1.c5 = t2.c5
AND t1.c6 = t2.c6
AND t2.ident = 'K_SDA_W');
EDIT1: 表的一些信息
EDIT2: 执行计划
--------------------------------------------------------------
| Id | Operation | Name |
--------------------------------------------------------------
| 0 | UPDATE STATEMENT | |
| 1 | UPDATE | table1 |
| 2 | NESTED LOOPS SEMI | |
| 3 | TABLE ACCESS FULL | table1 |
| 4 | TABLE ACCESS BY INDEX ROWID| table2 |
| 5 | INDEX RANGE SCAN | t2.c1 |
| 6 | COUNT STOPKEY | |
| 7 | TABLE ACCESS BY INDEX ROWID| table2 |
| 8 | INDEX RANGE SCAN | t2.PK |
--------------------------------------------------------------
答案 0 :(得分:0)
Table1
中的行数非常少,只需在此特定情况下删除WHERE
子句,并将NVL
添加到子查询返回的值中:
UPDATE table1 t1
SET t1.inxdc = NVL((SELECT sda_x
FROM table2 t2
WHERE t1.c1 = t2.c1
AND t1.c2 = t2.c2
AND t1.c3 = t2.c3
AND t1.c4 = t2.c4
AND t1.c5 = t2.c5
AND t1.c6 = t2.c6
AND t2.ident = 'K_SDA_W'
AND rownum=1), t1.inxdc);
一般来说,您的更新应该很快,您是否检查了子查询的性能?检查子查询的table2
上是否使用了索引(以及哪一个)(最好,向我们展示执行计划)。
答案 1 :(得分:0)
我认为表t2应该有一个关于c1,c2,c3,c4,c5,c6,缩进的索引 在这种情况下,t1的更新应该更快。