簡體   English   中英

當我嘗試在 oracle sql 中執行我的過程時出現“光標已打開”錯誤

[英]'Cursor is already open' error when I try to execute my procedure in oracle sql

I wrote a function in oracle sql to fetch the name of an employee whose id in the table matches the input given to the function.

 create or replace function id_search
    (
    x in number
    )
    return number
    is
    cursor e is select ename from employee where emp_id = x;
    begin
    open e;
   for i in e
   loop
   dbms_output.put_line('name is :'||i.ename);
   end loop;
   close e;
   return 0;
   end;
   /

在此之后,我在我編寫的程序中調用了這個 function:

SQL>     create or replace procedure id_searchP
  2      (
  3      y in number
  4      )
  5      is
  6      t number:= 1;
  7      begin
  8      t := id_search(y);
  9      end;
 10      /

但是,當我嘗試執行我的程序時,我遇到了錯誤:

SQL> exec id_searchP(2);
BEGIN id_searchP(2); END;

          *

ERROR at line 1:
ORA-06511: PL/SQL: cursor already open
ORA-06512: at "tom.ID_SEARCH", line 7
ORA-06512: at "tom.ID_SEARCH", line 10
ORA-06512: at "tom.ID_SEARCHP", line 8
ORA-06512: at line 1

為什么我會收到此錯誤?

您打開和關閉 cursor 兩次。 你不需要open e; 然后再次for i in e 我喜歡你的 function:

create or replace function id_search(x in number)
return number
is

    cursor e 
    is
    select ename 
    from employee 
    where emp_id = x;

begin

       for i in e loop
          dbms_output.put_line('name is :'||i.ename);
       end loop;

       return 0;
end;

然后程序就ok了:

create or replace procedure id_searchP(y in number)
is
     t number:= 1;
begin
     t := id_search(y);
end;

然后只需一個電話就足夠了:

BEGIN 
  id_searchP(2); 
END;

這是演示

您遇到此問題是因為您明確打開 cursor e,然后嘗試在 cursor e 上啟動 cursor for 循環。 但是,cursor for 循環會隱式嘗試打開您已顯式打開的 cursor e。

如果您想使用 cursor for 循環,則需要刪除顯式打開和關閉語句。

很少需要使用明確聲明的 cursor。 養成使用 cursor FOR 循環的習慣:

 create or replace function id_search(pinEmployee_ID in number)
    return number
 is
 begin
   for rowEmployee in (select ename
                         from employee
                         where emp_id = pinEmployee_ID)
   loop
     dbms_output.put_line('name is :' || rowEmployee.ename);
   end loop;

   return 0;
 end id_search;

那里 - 更短,更簡單,更不容易出錯,更容易理解。

請使用有意義的名稱。 我不在乎這是學校作業還是其他什么——使用有意義的名字。 不要讓人們深入研究您的代碼來弄清楚您的參數的含義或用途。

進一步 - 請花時間格式化您的代碼,使其可讀。 一致地縮進,確保代碼級別對肉眼可見,放入空格以便您的代碼可以輕松閱讀,正確拼寫和拼寫出來。 我不想看到i作為參數名稱 - 如果傳入的是(應該是)員工 ID,那么請確保參數名稱使這一點顯而易見。 計算機編程主要是一種溝通練習——在你、計算機和可憐的愚蠢 SOB 之間,十年后他們將不得不閱讀你的代碼並弄清楚它的作用。 當他們必須維護您的代碼時,不要成為每個人都詛咒的人。 現在養成良好的習慣。

編程是一門手藝。 如果這是您真正想做的事情,請努力做好。 每一個任務,每一個劇本,每一天都是一個改進的機會。 或者至少展示你所知道的。 確保您所展示的始終是您最好的。

暫無
暫無

聲明:本站的技術帖子網頁,遵循CC BY-SA 4.0協議,如果您需要轉載,請注明本站網址或者原文地址。任何問題請咨詢:yoyou2525@163.com.

 
粵ICP備18138465號  © 2020-2024 STACKOOM.COM