PLSQL語法


Procedural Language和SQL的結合體。通過增加變量、控制語句,使我們可以寫些邏輯更加復雜的數據庫操作

語句框架組成

declare – 可選 聲明各種變量或游標的地方。 begin – 必要 開始執行語句。 --單行注釋語句用兩個連在一起的‘-’表示。 /*多行注釋語句, 可以換行*/ exception – 可選 出錯后的處理。 end; – 必要(請注意end后面的分號)
        簡單helloworld程序
1 declare
2     v_temp number(6):=123; /* := 是一個賦值符號 */
3 begin
4     dbms_output.put_line('middle');
5     dbms_output.put_line(v_temp);
6 end;
注意

要想顯示程序的東西需要設置環境

 set serveroutput off -->關閉輸出(默認關閉)
 set serveroutput on -->打開輸出
基本數據類型
    • Number 數字型
    • Int 整數型
    • Pls_integer 整數型,產生溢出時出現錯誤
    • Binary_integer 整數型,表示帶符號的整數
    • Char 定長字符型,最大255個字符
    • Varchar2 變長字符型,最大2000個字符
    • Long 變長字符型,最長2GB
    • Date 日期型
    • Boolean 布爾型(TRUE、FALSE、NULL三者取一)
    • %type 表示不需要知道具體的一個字段類型,與指定的字段類型一致即可。例如:v_empno emp.empno%type;
    • %rowtype 與表結構完全一致 %rowtype 舉例:

 1 declare 
 2  v_tt emp%rowtype;
 3  begin
 4       select * into v_tt from emp where empno=7521;
 5       dbms_output.put_line(v_tt.job);
 6       dbms_output.put_line(v_tt.sal);
 7  end;
 8 
 9 輸出:SALESMAN
10      1250

varray

定義語法

TYPE VARRAYNAMEIS VARRAY(SIZE) OF ELEMENTTYPE [NOT NULL];

    • 其中,varrayname是VARRAY數據類型的名稱,size是正整數,表示可以容納的成員的最大數量,每個成員的數據類型是elementtypeo默認時,成員可以取空值,否則需要使用NOT NULL加以限制。

    • 數組是具有相同數據類型的一組成員的集合。每個成員都有一個唯一的下標,它取決於成員在數組中的位置。在PL/SQL中,數組數據類型是VARRAY(variable array,即可變數組)。

1 declare 
2     type my_varray is varray(2) of varchar2(12) not null;
3     varray_my my_varray;
4 begin
5     varray_my:=my_varray('dsa','sdafds');
6     dbms_output.put_line(varray_my(1));
7 end;
    • 如果初始化數量大於設定的大小,會報下標超出限制異常

    • 如果初始化數量小於設定的大小,會按照初始化數量進行設定大小,訪問不存在數據的下標(即使在設定范圍內).也會報異常

 1 DECLARE
 2     --定義一個最多保存5個VARCHAR(25)數據類型成員的VARRAY數據類型
 3     TYPE reg_varray_type IS VARRAY(5) OF VARCHAR(25);
 4     --聲明一個該VARRAY數據類型的變量
 5     v_reg_varray REG_VARRAY_TYPE;
 6 BEGIN
 7     --用構造函數語法賦予初值
 8     v_reg_varray := reg_varray_type
 9     ('中國', '美國', '英國', '日本', '法國');
10     DBMS_OUTPUT.PUT_LINE('地區名稱:'||v_reg_varray(1)||''
11     ||v_reg_varray(2)||''
12     ||v_reg_varray(3)||''
13     ||v_reg_varray(4));
14     DBMS_OUTPUT.PUT_LINE('賦予初值NULL的第5個成員的值:'||v_reg_varray(5));
15     --用構造函數語法賦予初值后就可以這樣對成員賦值
16     v_reg_varray(5) := '法國';
17     DBMS_OUTPUT.PUT_LINE('第5個成員的值:'||v_reg_varray(5));
18 END;

table

    • 定義記錄表(或索引表)數據類型。它與記錄類型相似,但它是對記錄類型的擴展。它可以處理多行記錄,類似於C語言中的二維數組,使得可以在PL/SQL中模仿數據庫中的表。
定義記錄表類型的語法如下:

TYPE TABLE NAME IS TABLE OF ELEMENT_TYPE [NOT NULL] INDEX BY [BINARYINTEGER|LSINTEGER|VARRAY2];

    • 關鍵字INDEX BY表示創建一個主鍵索引,以便引用記錄表變量中的特定行。 BINARY_INTEGER的說明
    • 如語句:TYPE NUMBERS IS TABLE OF NUMBER INDEX BY BINARYINTEGER;其作用是,加”INDEX BYBINARYINTEGER ”后,NUMBERS類型的下標就是自增長,NUMBERS類型在插入元素時,不需要初始化,不需要每次EXTEND增加一個空間。
    • 而如果沒有這句話“INDEXBY BINARY_INTEGER”,那就得要顯示對初始化,且每插入一個元素到NUMBERS類型的TABLE中時,都需要先EXTEND。

 1 --table 不能像varray一樣初始化數據,只能一個一個賦值
 2 declare
 3   type table_my is table of number not null index by binary_integer;-- by binary_integer表示創建一個主鍵索引,以便引用記錄表變量中的特定行。
 4   my_table table_my;
 5 begin 
 6   my_table(1):=23;
 7   my_table(2):=24;
 8   my_table(3):=24;
 9   dbms_output.put_line(my_table(1));
10 end;
11 
12 結果: 23
13 
14 
15 ---table結合rowtype的使用
16 declare
17 type table_my is table of emp%rowtype index by binary_integer;
18 
19 my_table table_my;
20 begin
21   select * BULK COLLECT into my_table from emp ;
22   for i in my_table.first..my_table.last loop
23     dbms_output.put_line(my_table(i).empno||'=='||my_table(i).ename||'=='||my_table(i).job);
24   end loop;
25 end;
26 
27 結果:1357==oracle==
28     7369==SMITH==CLERK
29     7499==ALLEN==SALESMAN
30     ...
table常見方法

record

    • 定義記錄數據類型。它類似於C語言中的結構數據類型(STRUCTURE),PL/SQL提供了將幾個相關的、分離的、基本數據類型的變量組成一個整體的方法,即RECORD復合數據類型。在使用記錄數據類型變量時,需要在聲明部分先定義記錄的組成、記錄的變量,然后在執行部分引用該記錄變量本身或其中的成員。
定義記錄數據類型的語法如下:

TYPE RECORDNAME IS RECORD(
  V1 DATA
TYPE1 [NOT NULL][:=DEFAULTVALUE],
  V2 DATATYPE2 [NOT NULL][:=DEFAULTVALUE],
  VN DATA
TYPEN [NOT NULL][:=DEFAULT_VALUE]
);

 

 1 ---record實現多列多行查詢
 2 declare
 3   type my_record is record(
 4        v_empno emp.empno%type,
 5        v_ename emp.ename%type,
 6        v_job emp.job%type
 7   );
 8   type  my_table is table of my_record index by binary_integer;
 9   table_my my_table;
10 begin
11   select empno,ename,job BULK COLLECT into table_my from emp ;
12   for i in table_my.first..table_my.last loop
13     dbms_output.put_line(table_my(i).v_empno||'=='||table_my(i).v_ename||'=='||table_my(i).v_job);
14   end loop;
15 end;
16 結果同上一個table

boolean

    • 布爾值只有TRUE, FALSE及 NULL 三個值

單行取值select

語法格式

select 字段 into 變量 from 表 where 條件

    1. 將查詢到得數據放入變量中
    2. 確保必須有唯一一個字段
    3. 不能存在多個值,也不能為空,否則報錯
    4. 將查詢到得數據放入變量中

異常處理,一級自定義異常

語法格式

EXCEPTION
  WHEN firstexception THEN code to handle first exception 
  WHEN second
exception THEN code to handle second exception
  WHEN OTHERS THEN code to handle others exception 
END;

    • 異常處理可以按任意次序排列,但 OTHERS 必須放在最后
常見異常

自定義異常:

 1 declare 
 2     v_exception exception;
 3     v_sal emp.sal%type;
 4 begin
 5   select sal into v_sal from emp where empno=7521;
 6   if v_sal>1000 then
 7     raise v_exception;
 8     else
 9       dbms_output.put_line('還可以');
10    end if;
11    exception
12      when v_exception then
13        dbms_output.put_line('錢太少啦'); 
14 end;
15 
16 結果:錢太少啦

自定義錯誤----------------

 1 declare 
 2 v_sal emp.sal%type;
 3 begin
 4   select sal into v_sal from emp where empno=7521;
 5   if v_sal>1000 then
 6     raise_application_error('-20000','工資太低啦');
 7     else
 8       dbms_output.put_line(v_sal);
 9   end if;
10 
11 end;
12 結果:會彈出彈出框錯誤

PLSQL嵌套DML的 insert update delete

    1. 直接使用
    2. DML語句起作用或者回退的話,需要顯式的調用commit或者rollback
    3. sql%rowcount屬性來記錄最后一條SQL語句影響了多少 條記錄
insert
 1 declare 
 2    v_empno emp.empno%type:=&s_empno;
 3  begin
 4    insert into emp(empno,ename) values(v_empno,'張三');
 5    if v_empno>4 then
 6      rollback;
 7      raise_application_error('-20000','不能這樣插滴~~');
 8    end if;
 9  end;
10 結果彈出錯誤.
update和delete用法同上

execute immediate的用法

    • 拼接字符串:標准的sql語句
    • execute immediate +字符串
    • execute immediate +字符串 into 變量 using 參數

- execute immediate 執行ddl語句或dml語句或dcl語句 (標准的sql語句)

 1   ----1--- 
 2    declare 
 3     v_sql varchar2(122):='insert into emp(empno,ename) values(:a,:b)';
 4    begin
 5      execute immediate v_sql using 111,'shfdk';
 6      commit;
 7    end;
 8 
 9    ----2-----
10    declare
11      v_sql  varchar2(122) := 'select ename from emp where sal=:a';
12      v_name emp.ename%type;
13    begin
14      execute immediate v_sql
15        into v_name
16        using 800;
17      dbms_output.put_line(v_name);
18    end;

循環結構

when
 1 打印偶數
 2 declare
 3   v_num number(3, 0) := 0;
 4 begin
 5   loop
 6     dbms_output.put_line(v_num);
 7     v_num := v_num + 2;
 8     exit when v_num = 100;
 9   end loop;
10 end;
for循環
 1 打印乘法口訣表
 2 begin
 3   for i in 1..9 loop
 4     for j in 1..i loop
 5       dbms_output.put(j||'*'||i||'='||(i*j)||chr(9));
 6       if i=j then  dbms_output.new_line();
 7       end if;
 8     end loop;
 9   end loop;
10 end;

 


免責聲明!

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



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