【发布时间】:2020-10-07 07:49:54
【问题描述】:
我在 proc 中有一个循环,它循环通过一个 ID。 CDID 可以有 4 种类型:
CDID TYPE
123 AA
456 BB
789 CC
999 DD
每种类型都有 4 个主要的 IF 块。虽然 CDID 不必具有所有 4 种类型,并且每个主 IF 块都由嵌套的 if 块组成。 在嵌套的 ifs 中,我使用选择查询将值插入到 4 个变量(不是表)中。在所有 4 个 IF 块的末尾,有一个更新语句,它获取 4 个变量的值并更新表。
下面是proc结构供大家参考:
CREATE OR REPLACE PROC MY_PROC
a varchar2;
b varchar2;
c varchar2;
d varchar2;
v_cnt number
BEGIN
FOR I IN (SELECT CDID FROM TABLE_A where column is null) --this table contains only 1 row for each id
BEGIN
select count(*) into v_cnt from TABLE_B where cdid=i.cdid and type='AA';
if v_count > 0 then
nested ifs
SELECT a,b,c,d INTO a,b,c,d from TABLE_B where cdid=i.cdid and type='AA'...;
end ifs...;
if v_count = 0 then --if count is zero of TYPE:AA
select count(*) into v_cnt from TABLE_B where cdid=i.cdid and type='BB';
if v_count > 0 then
nested ifs
select a,b,c,d INTO a,b,c,d from TABLE_B where cdid=i.cdid and type='BB'...;
end ifs...;
if v_count = 0 then --if count is zero of TYPE:BB
same thing continues for TYPES CC AND DD.
end if;
END;
UPDATE TABLE_A
SET COLUMN1=A,
COLUMN2=B,
COLUMN3=C,
COLUMN4=D
where cdid=i.cdid;
END LOOP;
END;
大约30k-35k 条记录,proc 需要 40 分钟才能执行。在上面的proc中,对于每个cdid,它可以检查多个if。
我无法确定如何微调此过程。如何批量处理记录?
【问题讨论】:
-
希望你已经进行了search。没有任何帮助?
-
当你说
approx. 30k-35k records你指的是哪个表?您有可用于 id 列的索引吗? -
SQL 和 PL/SQL 之间的上下文切换代价高昂,因为检查 any 行是否存在的不必要计数也是如此。你在循环中得到了两个单独的选择。计数可以通过使用游标来解决。这也将使您的代码更清晰。
-
@0xdb...是的,我做到了。
-
@Sujitmohanty30... 它适用于 table_A,因为它必须遍历 table_a 的 id'f,然后对于每个 id,在嵌套的 if 块中对 table_b 运行 select。
标签: oracle stored-procedures plsql query-performance execution-time