使用LOOP

时间:2017-08-21 12:58:17

标签: oracle plsql bulk-collect

http://www.oracle.com/technetwork/issue-archive/2008/08-mar/o28plsql-095155.html

在这个页面中,他们提到了:

  

当您使用BULK COLLECT和集合从光标中获取数据时,您不应该依赖游标属性来决定是否终止循环和数据处理。

他提到,为了确保我们的查询处理所有行,我们应该

不使用:

  

退出时

     

光标%NOTFOUND;

我们应该使用:

  

退出时

     

collectionvariable.count = 0;

是什么原因?

1 个答案:

答案 0 :(得分:3)

文章明确指出,在使用cur%NOTFOUND时,它会跳过处理某些记录。

请检查自包含的示例:

DECLARE
  TYPE item_tab IS TABLE OF PLS_INTEGER;
  l_item item_tab;
  CURSOR get_item_value IS
  SELECT LEVEL
  FROM dual
  CONNECT BY LEVEL <= 25;
BEGIN
  OPEN get_item_value;
  LOOP
     FETCH get_item_value BULK COLLECT INTO l_item LIMIT 10;  -- 10    10    5
     EXIT WHEN get_item_value%NOTFOUND;                       -- FALSE FALSE TRUE
     DBMS_OUTPUT.put_line(l_item.COUNT);       
  END LOOP;
  CLOSE get_item_value;
END;

输出:

10
10
-- 5 record left

第二个版本:

DECLARE
  TYPE item_tab IS TABLE OF PLS_INTEGER;
  l_item item_tab;
  CURSOR get_item_value IS
  SELECT LEVEL
  FROM dual
  CONNECT BY LEVEL <= 25;
BEGIN
  OPEN get_item_value;
  LOOP
     FETCH get_item_value BULK COLLECT INTO l_item LIMIT 10;   -- 10   10   5   0
     EXIT WHEN l_item.COUNT = 0;                               -- F    F    F   T
     DBMS_OUTPUT.put_line(l_item.COUNT);
  END LOOP;
  CLOSE get_item_value;
END;

输出:

10
10
5