1.概述sql
PL/SQL(Procedural Language/Structured Query Language)是Oracle對標準數據庫語言SQL的過程化擴充,它將數據庫技術和過程化程序設計語言聯繫起來,是一種應用開發語言,可以使用循環,分支處理數據,將SQL的數據操縱功能與過程化語言數據處理功能結合起來。 PL/SQL的使用,使SQL成爲一種高級程序設計語言,支持高級語言的塊操做,條件判斷,循環語句,嵌套等,與數據庫核心的數據類型集成,使SQL 的程序設計效率更高。(更加詳細的介紹,你們能夠Google一下)數據庫
PL/SQL程序主要分爲兩大類:匿名程序和命名程序。下面先講匿名程序。一個典型的匿名塊結構分爲如下幾個部分:編程
DECLARE--可選部分 --變量、常量、遊標、用戶定義異常的聲明 BEGIN--必要部分 --SQL語句和PL/SQL語句構成的執行程序 EXCEPTION--可選部分 --程序出現異常時,捕捉異常並處理異常 END;--必須部分,注意END後面的分號
按照上面的格式,咱們先寫一個簡單完整的匿名塊:數組
DECLARE v_counter NUMBER(3); v_user ALL_USERS.USERNAME%TYPE; v_today DATE; BEGIN SELECT SYSDATE,USER INTO v_today,v_user FROM DUAL; DBMS_OUTPUT.PUT_LINE( 'today:' || TO_CHAR(v_today,'YYYY-MM-DD')); DBMS_OUTPUT.PUT_LINE('Schema:' || v_user); v_counter:=0; LOOP v_counter:=v_counter + 1; EXIT WHEN v_counter > 10; DBMS_OUTPUT.PUT_LINE('line:' || v_counter); END LOOP; EXCEPTION WHEN OTHERS THEN --Do log operations --COMMIT; END;
下面逐一解釋:安全
定義了三個變量:v_counter,number類型;v_user,ALL_USERS視圖中USERNAME字段的類型(XX%TYPE的意思就是表示XX的類型);v_today,DATE類型。編程語言
將當前日期和當前用戶查詢出來分別賦值給v_today和v_user變量,並將兩者打印輸出;函數
打印從0到9這10個數字。v_counter充當迭代用的變量。lua
有異常出現時怎麼處理。spa
結束部分就是按格式寫上就好,沒什麼好說的。操作系統
上面的例子中還出現了單行註釋,也就是以--開頭的一行都會被視爲註釋。此外,PL/SQL還支持多行注視/* */。此外,對於PL/SQL的標識符來講,必須以字符開頭,而且最大不超過30個字符,這一點與不少語言略有不一樣。還要特別說的一點是,PL/SQL的字符串字面量是用單引號'括起來的。
2.常量與變量
PL/SQL的變量定義的格式以下:
VARIABLE_NAME DATATYPE;
變量的類型必須給出,能夠是全部PL/SQL支持的類型,具體有哪些咱們後面會繼續講。此外,在定義變量的時候能夠給變量給出初始值,像下面這樣:
VARIABLE_NAME DATATYPE := INIT_VALUE;
PL/SQL的賦值操做符是:= ,若是沒有給出初始值,那麼變量默認的初始值是NULL。
定義常量的方法與定義變量的方法基本相似,只是須要加上關鍵字CONSTANT,而且必須給定初始值,以下:
VARIABLE_NAME CONSTANT DATATYPE := INIT_VALUE;
定義常量時必須給出常量值,而且一旦賦值,以後就不容許再改變了。下面是一個例子:
--常量值不可變例子 DECLARE v_name CONSTANT VARCHAR2(8) := 'Tom'; BEGIN v_name := 'Jerry'; DBMS_OUTPUT.put_line(v_name); END; /
運行上面的程序,Oracle會報錯:
ORA-06550: 第 5 行, 第 3 列: PLS-00363: 表達式 'V_NAME' 不能用做賦值目標 ORA-06550: 第 5 行, 第 3 列: PL/SQL: Statement ignored
PL/SQL中,常量、變量支持的全部類型以及詳細的解釋建議你們結合你使用的Oracle版本參考Oracle官方文檔,版本之間會有一些微小調整。這裏簡要的列舉一些:
CHAR(N):N位字符,不足N位,自動用空格補全。N必需要指定。 VARCHAR2(N):最多N位字符,N能夠不指定,默認爲1。不足N位時,不會用空格補全N位。所以,用的比較多。 DATE:日期時間類型,默認按照數據庫要求的格式顯示。 NUMBER(N,M):數字型。N位數字,其中M位爲小數的位數。 BOOLEAN:SQL中不支持這個類型,可是PL/SQL支持,有TRUE和FALSE兩種。 LONG:能夠接收很長的字符數據,多達32760字節。 RAW:接收二進制數據,長度達到32767字符。PL/SQL沒法解析其內容。 LONG RAW:比RAW更大而已。 MLSLABEL:安全操做系統標籤,Trusted Oracle中使用。 ROWID:用來惟一表示記錄在數據庫中的物理存儲地址的一種類型。Oracle會自動爲每條記錄添加這個僞列。 BLOB:最大4GB的二進制數據。 CLOB:最大4GB的文本數據。 NCLOB:多字節字符的BLOB。好比存儲漢字。 BFILE:一個指向OS文件的指針。 BINARY_INTEGER INT/INTEGER:整數 SMALLINT:小一點的整數。 POSITIVE:正數 NATURAL:天然數 NUMERIC/DEC/DECIMAL:相似於NUMBER REAL/FLOAT:浮點數 TABLE:符合類型,相似於數組 RECORD:複合類型,表示一條記錄
在聲明部分,不只能夠定義像上面那種的常量或者變量,還能夠聲明顯式遊標或者用戶自定義的異常。關於遊標和異常後面的文章還會討論。
3.執行部分
這個部分其實是咱們真正處理任務的一些操做,能夠說是PL/SQL塊中最重要的部分。主要包括表達式、賦值語句、條件語句、比較語句、循環、遊標控制語句:
表達式並非單獨的語句,而是包含在單獨語句中的小的代碼單元。表達式通常主要用在賦值語句和條件語句中。表達式又分爲算術表達式和比較表達式。這個和不少第三代語言是相似的,這裏就不贅述。
幾乎全部的SQL函數均可以以用做表達式,例如函數SUBSTR:
SUBSTR(v_str,m,n);
這就是一個合法的表達式。在PL/SQL中,惟一不能做爲表達式的SQL函數是DECODE函數,由於,在PL/SQL中,已經有了IF-THEN-END語句能夠替代它。
表達式之間還能夠經過邏輯運算符鏈接起來。這一點也是比較簡單的。
賦值語句上面已經見到了,經過賦值運算符:=實現賦值操做。所以,PL/SQL中的等於使用=實現的,不一樣於C語言中的==。
條件語句無非是if語句及其各類變種。PL/SQL的格式稍微有點不一樣,最簡單的形式以下:
IF(...) THEN --DO STH ELSE --DO STH ELSE END IF;
這是最簡單的一種形式。C語言中還有else if的形式,PL/SQL中也有,以下:
IF () THEN --A ELSIF () THEN --B ELSE --C END IF;
使用上就和別的語言沒有什麼差異,只是初學的時候須要注意一下寫法格式
循環是編程語言中很是重要的一種結構,它用於對一組操做對象執行某一組相同的操做。循環有不少種不一樣的形式,下面一一介紹:
形式1:
LOOP --作若干操做 EXIT WHEN ...;--何時退出循環 END LOOP;
第一部分的例子中就用到了這種形式的循環了。
形式2:
LOOP --作若干操做 IF ...--何時退出循環 THEN EXIT; END IF; END LOOP;
和形式1實際上是等價的
形式3:while循環
WHILE(v_i < 10) LOOP ----作若干操做 v_i := v_i + 1; END LOOP;
形式4:數值FOR循環
FOR v_i IN 1..10 LOOP --作一些操做 END LOOP;
形式5:遊標FOR循環
這一部分,咱們在後面講到遊標的時候再講。
下面,咱們先用四種形式打印數字1-10,代碼以下:
--形式1 DECLARE v_limit number(2) := 1; BEGIN LOOP DBMS_OUTPUT.PUT_LINE(v_limit); v_limit := v_limit + 1; EXIT WHEN v_limit > 10; END LOOP; END; / --形式2 DECLARE v_limit number(2) := 1; BEGIN LOOP IF v_limit > 10 THEN EXIT; END IF; DBMS_OUTPUT.PUT_LINE(v_limit); v_limit := v_limit + 1; END LOOP; END; / --形式3 DECLARE v_limit number(2) := 1; BEGIN WHILE v_limit <= 10 LOOP DBMS_OUTPUT.PUT_LINE(v_limit); v_limit := v_limit + 1; END LOOP; END; / --形式4 DECLARE v_limit number(2) := 1; BEGIN FOR v_limit IN 1..10 LOOP DBMS_OUTPUT.PUT_LINE(v_limit); END LOOP; END; /
PS:
1.運行上面的PL/SQL程序可能會沒有輸出,這是由於Oracle默認沒有打開serveroutput選項,只須要在SQL PLUS中執行:
SET SERVEROUTPUT ON;
2.上面代碼片斷後面的/不是代碼自己的內容,而是讓SQLPLUS馬上運行這段代碼的一個操做。
關於遊標相關的內容,下一篇博客專門討論。