46.異常
(1)
declare v_temp number(4); begin select empno into v_temp from emp where deptno = 10; exception when too_many_rows then dbms_output.put_line('太多記錄了'); when others then dbms_output.put_line('error'); end;
(2)
declare v_tempnumber(4); begin select empno into v_temp from emp where empno = 2222; exception when no_data_found then dbms_output.put_line('沒有該項資料'); end; ----------------錯誤記錄日誌(用表記錄:將系統日誌存到資料庫便於以後查看) ----------- 建立序列(用來處理遞增的ID): create sequence seq_errorlog_id start with 1 increment by 1; 建立日誌表: create table errorlog ( id number primary key, errcode number, errmsg varchar2(1024), errdate date ); 樣本程式: declare v_deptno dept.deptno%type := 10; v_errcode number; v_errmsg varchar2(1024); begin delete from dept where deptno = v_deptno; commit; exception when others then rollback; v_errcode:= SQLCODE; v_errmsg:= SQLERRM; insert into errorlog values (seq_errorlog_id.nextval, v_errcode,v_errmsg, sysdate); commit; end;
47. PL/SQL中的重點cursor(遊標)和指標的概念差不多
declare cursorc is select * from emp; //此處的語句不會立刻執行,而是當下面的open c的時候,才會真正去資料庫中取資料 v_emp c%rowtype; begin open c; fetch c into v_emp; dbms_output.put_line(v_emp.ename); //這樣會只輸出一條資料 134將使用迴圈的方法輸出每一條記錄 close c; end; ----------------------使用do while 迴圈遍曆遊標中的每一個資料--------------------- declare cursor c is select* from emp; v_emp c%rowtype; begin open c; loop fetch c into v_emp; (1) exit when(c%notfound); //notfound是oracle中的關鍵字,作用是判斷是否還有下一條資料 (2) dbms_output.put_line(v_emp.ename); //(1)(2)的順序不能顛倒,否則會把最後一條結果再多列印一次。 end loop; close c; end; ------------------------使用while迴圈,遍曆遊標--------------------- declare cursor c is select* from emp; v_emp emp%rowtype; begin open c; fetch c into v_emp; while(c%found) loop dbms_output.put_line(v_emp.ename); fetch c into v_emp; end loop; close c; end;s ------------------------使用for 迴圈,遍曆遊標(最方便快捷的方法。)----------------- declare cursorc is select * from emp; begin for v_emp in c loop dbms_output.put_line(v_emp.ename); endloop; end;
帶參數的遊標(相當於函數)
declare cursor c(v_deptno emp.deptno%type, v_job emp.job%type) is select ename, sal from emp where deptno=v_deptno and job=v_job; begin forv_temp in c(30, 'CLERK') loop dbms_output.put_line(v_temp.ename); endloop; end;
可更新的遊標
declare cursorc is select * from emp2 for update; begin for v_temp in c loop if(v_temp.sal< 2000) then update emp2 set sal = sal * 2 where current of c; elsif (v_temp.sal =5000) then deletefrom emp2 where current of c; end if; end loop; commit; end;
48. store procedure預存程序(帶有名字的程式塊)
createor replace procedure p is--除了這兩句替代declare,下面的語句全部都一樣 cursor c is select * from emp2 for update; begin for v_emp in c loop if(v_emp.deptno= 10) then updateemp2 set sal = sal +10 where current of c; elseif(v_emp.deptno =20) then updateemp2 set sal = sal + 20 where current ofc; else updateemp2 set sal = sal + 50 where current of c; endif; end lo