2013-02-04 23 views
6

Bất kỳ ai có bất kỳ ý tưởng nào về lý do tại sao hệ thống cho tôi biết rằng PAR_CUR đã mở? Tất cả mọi thứ đã làm việc tốt cho đến khi tôi thêm con trỏ bên ngoài nhất (dup_cur) và bây giờ tôi nhận được lỗi này. Cảm ơn bạn đã giúp đỡ bất kỳ bạn có thể có. Các dữ liệu dưới đây là tốt.ORA-06511: Con trỏ PL/SQL đã mở

Lỗi báo cáo:

ORA-06511: PL/SQL: cursor already open 
ORA-06512: at line 18 
ORA-06512: at line 61 
06511. 00000 - "PL/SQL: cursor already open" 
*Cause: An attempt was made to open a cursor that was already open. 
*Action: Close cursor first before reopening. 

Mã sản phẩm:

ACCEPT p_1 prompt 'PLEASE ENTER THE REGION:' 
DECLARE 
    v_child  regions.child_name%TYPE := '&p_1'; 
    v_parent  regions.parent_name%TYPE; 
    v_parent2  regions.child_name%TYPE; 
    v_parent3  regions.child_name%TYPE; 
    v_count  NUMBER := 0; 
    v_regionnumber NUMBER := 1; 
    v_parentcount NUMBER := 0; 
    v_dup   regions.child_name%TYPE; 
    CURSOR reg_cur IS 
     SELECT Upper(parent_name) 
     FROM regions 
     WHERE Upper(child_name) = Upper(v_child) 
      AND Upper(parent_name) = Upper(v_dup); 
    CURSOR par_cur IS 
     SELECT Upper(parent_name) 
     FROM regions 
     WHERE Upper(child_name) = v_parent 
      AND parent_name IS NOT NULL; 
    CURSOR dup_cur IS 
     SELECT Upper(parent_name) 
     FROM regions 
     WHERE Upper(child_name) = Upper(v_child); 

BEGIN MỞ dup_cur;

LOOP 
     FETCH dup_cur INTO v_dup; 
     EXIT WHEN dup_cur%NOTFOUND; 

     SELECT Count(*) 
     INTO v_count 
     FROM regions 
     WHERE Upper(child_name) = Upper(v_child); 

     SELECT Count(parent_name) 
     INTO v_parentcount 
     FROM regions 
     WHERE Upper(parent_name) = Upper(v_child); 

     IF v_count > 0 
      OR v_parentcount > 0 THEN 
      SELECT Count(parent_name) 
      INTO v_count 
      FROM regions 
      WHERE Upper(child_name) = Upper(v_child); 

      IF v_count > 0 THEN 
      OPEN reg_cur; 

      FETCH reg_cur INTO v_parent; 

      dbms_output.Put_line('----- Begin Output -----'); 

      LOOP 
       IF v_regionnumber < 2 THEN 
        dbms_output.Put_line('Line 1: (Region 1) ' 
             || Upper(v_child)); 

        dbms_output.Put_line('Line 2: (Region 1) ' 
             || Upper(v_child) 
             || ' --> ' 
             || '(Region 2) ' 
             || Upper (v_parent)); 
       END IF; 

       OPEN par_cur; 

       v_parent2 := v_parent; 

       FETCH par_cur INTO v_parent; 

       EXIT WHEN par_cur%NOTFOUND; 

       v_regionnumber := v_regionnumber + 1; 

       IF v_regionnumber = 2 THEN 
        dbms_output.Put_line('Line 3: ' 
             || '(Region 1) ' 
             || Upper(v_child) 
             || ' --> ' 
             || '(Region 2) ' 
             || Upper(v_parent2) 
             || ' --> ' 
             || '(Region 3) ' 
             || Upper(v_parent)); 
       ELSE 
        IF v_regionnumber = 3 THEN 
        dbms_output.Put_line('Line 4: ' 
             || '(Region 1) ' 
             || Upper(v_child) 
             || ' --> ' 
             || '(Region 2) ' 
             || Upper(v_parent3) 
             || ' --> ' 
             || '(Region 3) ' 
             || Upper(v_parent2) 
             || ' --> ' 
             || '(Region 4) ' 
             || Upper(v_parent)); 
        END IF; 
       END IF; 

       CLOSE par_cur; 

       v_parent3 := v_parent2; 
      END LOOP; 

      dbms_output.Put_line('----- End_Output -----'); 

      CLOSE reg_cur; 
      ELSE 
      dbms_output.Put_line('----- Begin Output -----' 
           || Chr(10) 
           || 'Line 1: (Region 1) ' 
           || Upper(v_child) 
           || Chr(10) 
           || '----- End_Output -----'); 
      END IF; 
     ELSE 
      dbms_output.Put_line('----- Begin Output -----' 
           || Chr(10) 
           || Upper(v_child) 
           ||' is not in the table.' 
           || Chr(10) 
           || '----- End_Output -----'); 
     END IF; 
    END LOOP; 

    CLOSE dup_cur; 
END; 




CREATE TABLE regions 
(
     PARENT_NAME  VARCHAR2(30), 
     CHILD_NAME  VARCHAR2(30) 
); 
INSERT INTO regions VALUES('Texas','Rockford'); 
INSERT INTO regions VALUES('Colorado','Aurora'); 
INSERT INTO regions VALUES(NULL,'Asia'); 
INSERT INTO regions VALUES(NULL,'Australia'); 
INSERT INTO regions VALUES(NULL,'Europe'); 
INSERT INTO regions VALUES(NULL,'North America'); 
INSERT INTO regions VALUES('Asia','China'); 
INSERT INTO regions VALUES('Asia','Japan'); 
INSERT INTO regions VALUES('Australia','New South Wales'); 
INSERT INTO regions VALUES('New South Wales','Sydney'); 
INSERT INTO regions VALUES('Canada','Ontario'); 
INSERT INTO regions VALUES('China','Beijing'); 
INSERT INTO regions VALUES('England','London'); 
INSERT INTO regions VALUES('Europe','United Kingdom'); 
INSERT INTO regions VALUES('Illinois','Aurora'); 
INSERT INTO regions VALUES('Illinois','Chicago'); 
INSERT INTO regions VALUES('Illinois','Rockford'); 
INSERT INTO regions VALUES('Wisconsin','Madison'); 
INSERT INTO regions VALUES('Japan','Osaka'); 
INSERT INTO regions VALUES('Japan','Tokyo'); 
INSERT INTO regions VALUES('North America','Canada'); 
INSERT INTO regions VALUES('North America','United States'); 
INSERT INTO regions VALUES('Ontario','Ottawa'); 
INSERT INTO regions VALUES('Ontario','Toronto'); 
INSERT INTO regions VALUES('United States','Colorado'); 
INSERT INTO regions VALUES('United States','Illinois'); 
INSERT INTO regions VALUES('United States','Texas'); 
INSERT INTO regions VALUES('United Kingdom','England'); 
COMMIT; 

Trả lời

8

bạn đang mở và đóng con trỏ trong vòng lặp. bạn nên mở và đóng nó ra ngoài vòng lặp.

tức là.

FETCH REG_CUR INTO V_PARENT; 
DBMS_OUTPUT.PUT_LINE('----- Begin Output -----'); 
OPEN PAR_CUR; -- ************OPEN HERE 
LOOP 
    IF V_REGIONNUMBER < 2 THEN 
    DBMS_OUTPUT.PUT_LINE('Line 1: (Region 1) ' || UPPER(V_CHILD)); 
    DBMS_OUTPUT.PUT_LINE('Line 2: (Region 1) ' || UPPER(V_CHILD) || ' --> ' || '(Region 2) ' || UPPER (V_PARENT)); 
    END IF; 
    V_PARENT2 := V_PARENT; 
    FETCH PAR_CUR INTO V_PARENT; 
    EXIT WHEN PAR_CUR%NOTFOUND; 
    V_REGIONNUMBER := V_REGIONNUMBER + 1; 
    IF V_REGIONNUMBER =2 THEN 
    DBMS_OUTPUT.PUT_LINE('Line 3: ' || '(Region 1) '|| UPPER(V_CHILD) || ' --> ' || '(Region 2) ' || UPPER(V_PARENT2) || ' --> ' || '(Region 3) ' || UPPER(V_PARENT)); 
    ELSE 
    IF V_REGIONNUMBER =3 THEN 
     DBMS_OUTPUT.PUT_LINE('Line 4: ' || '(Region 1) '|| UPPER(V_CHILD) || ' --> ' || '(Region 2) ' || UPPER(V_PARENT3) || ' --> ' || '(Region 3) ' || UPPER(V_PARENT2)|| ' --> ' || '(Region 4) ' || UPPER(V_PARENT)); 
    END IF; 
    END IF; 
    V_PARENT3 := V_PARENT2; 
END LOOP; 
CLOSE PAR_CUR;-- ************CLOSE HERE 

như bạn đã mở trong vòng lặp, trên lặp thứ 2, các lỗi con trỏ như đã mở

tái bút: mình có vẻ như bạn đang cố gắng tìm ra hệ thống phân cấp và in nó. nếu vì vậy bạn chỉ có thể làm điều này:

SQL> select ltrim(str, ' --> ') str 
    2 from (select child_name, level, SYS_CONNECT_BY_PATH('(Region ' || level || ') ' || child_name, ' --> ') str, 
    3     parent_name 
    4   from regions 
    5   start with child_name = 'Rockford' 
    6   connect by child_name = prior parent_name) 
    7 where parent_name is null 
    8/

STR 
-------------------------------------------------------------------------------- 
(Region 1) Rockford --> (Region 2) Illinois --> (Region 3) United States --> (Re 
gion 4) North America 

(Region 1) Rockford --> (Region 2) Texas --> (Region 3) United States --> (Regio 
n 4) North America 


SQL> select ltrim(str, ' --> ') str 
    2 from (select child_name, level, SYS_CONNECT_BY_PATH('(Region ' || level || ') ' || child_name, ' --> ') str, 
    3     parent_name 
    4   from regions 
    5   start with child_name = 'London' 
    6   connect by child_name = prior parent_name) 
    7 where parent_name is null 
    8/

STR 
-------------------------------------------------------------------------------- 
(Region 1) London --> (Region 2) England --> (Region 3) United Kingdom --> (Regi 
on 4) Europe 


SQL> 
5

của nó (nói chung) nên sử dụng cú pháp này khi mở bất kỳ con trỏ

IF reg_cur %ISOPEN THEN 
    CLOSE reg_cur ; 
    END IF; 
    OPEN reg_cur ; 

hy vọng điều này sẽ giúp ...

Các vấn đề liên quan