游標,存儲過程


1.1什么是游標

用於臨時存儲一個查詢返回的多行數據(結果集,類似於java的jdbc連接返回的ResultSet集合),通過遍歷游標,可以逐行訪問處理該結果集的數據.

游標的使用方式:  聲明---打開--讀取---關閉

1.2語法

游標聲明:

CURSOR 游標名(參數列表)  IS 查詢語句;

游標的打開:

OPEN 游標名

游標的取值:

FETCH 游標名 INTO 變量列表

游標的關閉:

CLOSE 游標名

1.3游標的屬性

游標的屬性 返回值類型 說明
%ROWCOUNT 整型 獲取FETCH語句返回的數據行數
%FOUND 布爾型 最近的FETCH語句返回一行數據則為真,否則為加
%NOTFOUND 布爾型 與%FOUND屬性返回值相反
%ISOPEN 布爾型 游標已經打開時值為真,否則為假

 

其中%NOTFOUND是在游標中找不到元素的時候返回TRUE,通常用來判斷退出循環

1.4創建和使用

示例:使用游標查詢emp表中的所有員工的姓名和工資,並將其依次打印出來

-- 使用游標查詢emp表中的所有員工的姓名和工資,並將其依次打印出來
declare 
  -- 聲明游標 CURSOR 游標名(參數列表)  IS 查詢語句;
  CURSOR c_emp IS select ename,sal FROM emp;
  --聲明變量接收游標中的數據
  v_ename emp.ename%TYPE;
  v_sal    emp.sal%TYPE;
begin
  -- 打開游標
  OPEN c_emp;
  
  --遍歷游標
  LOOP
    --獲取游標中的數據   如果有的話賦值給變量
    FETCH c_emp INTO v_ename,v_sal;
    
    EXIT WHEN c_emp%NOTFOUND;
    dbms_output.put_line('姓名:'||v_ename||',薪水:'||v_sal);
  END LOOP;
  --關閉游標
  CLOSE c_emp;
  
end;

  

1.5帶參數的游標

示例:使用游標查詢並打印某部門的員工的姓名和薪資,部門編號為運行時手動輸入.

-- 使用游標查詢並打印某部門的員工的姓名和薪資,部門編號為運行時手動輸入.
declare 
  -- 聲明游標 CURSOR 游標名(參數列表)  IS 查詢語句;
  CURSOR c_emp(v_deptno emp.deptno%TYPE) IS
   select ename,sal FROM emp where deptno=v_deptno;
  --聲明變量接收游標中的數據
  v_ename emp.ename%TYPE;
  v_sal    emp.sal%TYPE;
begin
  -- 打開游標
  OPEN c_emp(20);
  
  --遍歷游標
  LOOP
    --獲取游標中的數據   如果有的話賦值給變量
    FETCH c_emp INTO v_ename,v_sal;
    
    EXIT WHEN c_emp%NOTFOUND;
    dbms_output.put_line('姓名:'||v_ename||',薪水:'||v_sal);
  END LOOP;
  --關閉游標
  CLOSE c_emp;
  
end;

 給對應級別的員工漲工資,key是empno

 

-- 給對應級別的員工漲工資,key是empno 
declare 
  -- 聲明光標
  cursor cemp is
   select empno,job from emp;
   --聲明變量接收光標數據
   pempno emp.empno%TYPE;
   pempjob emp.job%TYPE;
begin
  -- 事務回滾
  rollback;
  --打開光標
  open cemp;
  loop
    --遍歷光標取出一個員工
    fetch cemp into pempno,pempjob;
    --退出條件
    exit when cemp%notfound;
    --判斷員工的職位
    if pempjob='PRESIDENT' then update emp set sal=sal+1000 where empno=pempno;
     -- if condition then block ;elsif condition then block;else block;end if;
     elsif pempjob='MANAGER' then update emp set sal=sal+800 where empno=pempno;
     else update emp set sal=sal+400 where empno=pempno;
     end if;

    end loop;
  --關閉光標
  close cemp;
  -- oracle的默認事務隔離級別是read committed
   --事務的ACID 原子性、一致性、隔離性、持久性
 commit;

end;

存儲過程和存儲函數

數據庫存儲過程:指存儲在數據庫中供所有用戶程序調用的子程序叫存儲過程、存儲函數

·相同點:完成特定功能的程序
·不同點:是否用return語句返回值。存儲函數可以return返回值。存儲過程不可以通過return語句返回函數值。

1.創建存儲過程

create or replace procedure 過程名(參數列表)
as
begin
..........PLSQL子程序體;
end;

2.執行存儲過程

--1.exec 存儲過程名();
--2.begin
     存儲過程名();
    end;
帶參數的存儲過程
 舉例:為指定的員工,漲100塊錢的工資;並且打印漲前和漲后的薪水
1、創建一個帶參數的存儲過程:
 給執行的員工漲100塊錢的工資,並且打印漲前和漲后的薪水
create or replace procedure raisesalary(eno in number)
as
--定義一個變量保存漲前的薪水
 psal emp.sal%TYPE;
 begin
   --得到員工漲前的薪水
   select sal into psal from emp where empno=eno;
   --給員工漲100
   update emp set sal=sal+100 where empno=eno
   --需不需要commit?
   --注意:一般不在存儲過程或存儲函數中,commit和rollback
   --打印
   dbms_output.put_line('漲前:'||psal||'漲后:'(pasl+100))
 end;
--2、如何調用:
 begin
  raisesalary(7839);
  raisesalary(7566);
 commit;
 end;

存儲過程的調試

1.調試存儲過程最好放到Oracle數據庫所在的系統或虛擬機上,解壓SQL developer ,雙擊運行。
2.為了確保存儲過程或函數是可調試的,右鍵“以編譯並進行調試”,點擊紅色按鈕“調試”
3.利用已寫好的調用函數進行調試。

1.函數的定義

  是一個命名的存儲程序,可帶參數,並返回一個計算值。必須有return 子句,用於返回函數值。

2.創建存儲函數語法

  create or replace function 函數名(參數列表)
  return 函數值類型
  as
  begin
    PLSQL子程序體;
  end;

3.表達式中某個字段為空時,表達式返回值為空。為防止含有表達式的返回值錯誤,在可能為空的字段上加上NVL(字段名,0)。

--查詢某個員工的年收入

 

create or replace function queryemp_income(eno number) return number
as 
    --定義變量接收薪水和獎金
    p_sal emp.sal%type;
    p_comm emp.comm%type;
begin

  select sal,comm into p_sal,p_comm from emp where empno=eno;
  --nvl為遇空函數,如果p_comm為空則返回0
  return nvl(p_comm,0)+p_sal*12;
end;

1.存儲過程和存儲函數的區別

  存儲函數可以有一個返回值,存儲過程沒有返回值

2.in out 參數

  存過和函數都可以通過out 指定一個或多個輸出參數。可以利用out參數,實現多個返回值。

3.使用存過和存儲函數的原則

  只有一個返回值的話,用存儲函數;否則,用存儲過程。

 

create or replace procedure query
(eno in number,
 pename out varchar2,
psal out  number,
pjob out varchar2
 )
as
begin
select ename,sal,job into pename,psal,pjob from emp where  empno=eno;
end;

  

 

 

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM