儲存程式分類
在mysql.exe用戶端裡寫儲存程式的";"分割符問題
這個問題來自mysql.exe用戶端本身以";"作為語句的分隔字元(結束符)本身。而大部分的管理、開發mysql的應用程式均類似於mysql.exe,所以必須通過delimiter這個mysql伺服器可識別的命令來臨時修改伺服器認可的有效語句分隔字元
儲存程式組成結構
[label name]
begin
[declare 普通變數|declare異常別名];
[declare 異常別名|declare普通變數];
[declare 遊標;]
[declare 異常處理;]
[begin end 複合陳述式;]
[迴圈語句;]
[條件陳述式;]
......
end [{lable name}]
//
declare本地變數
declare va11 [,var2] [,...] date_type [default value --可以是運算式、常量]
- 本地變數聲明時要注意先後順序:普通變數、遊標、操作符
- 本地變數可以一次聲明同類型的多個變數 --類似於c語言,不同於postgresql、oracle;不可以指定[not] null 約束;不可以聲明為constant 變數
- 本地變數可以有初始化的default值,否則為null
- 本地變數可以向內層begin end 符合語句傳遞,除非她被內層同名變數overide
- 本地變數名字不要和表列同名,在過程內,本地變數總是優先被採用
set變數賦值
set var1 = value1 [,var2 = value2] [,....]
mysql的set語句可以對本地變數、系統變數、使用者自訂變數賦值,而不僅僅是本地變數!
select變數賦值 必須返回0行或 1 行 記錄
select col1 [,col2] [,exp1] [,exp2] [,....] into val1 [,val2] [,val3] [,val4] [,....] from table_express
- 如果select沒有返回資料,mysql有no data 的警告:warning with error code 1329 產生,變數保持原值
- 如果select返回多行資料,mysql或發生錯誤!可以通過limit 1 來限制。
mysql的異常處理
declare conditon_name condition for {sqlstate [value] 'sqlvalue'|mysql_error_code} --定義異常:目的是找一個含義更明顯或更適合的名稱;可理解為別名。
declare {continue|exit|undo} handler for {sqlstate [value] 'sqlvalue'|mysql_error_code|conditon_name
|sqlwarning|notfound|sqlexception} [,....] --定義異常處理mysql的異常處理
- 類似於其他過程化sql語言的錯誤處理,只是結構和使用方法不同(postgresql、oracle都是固定的塊結構的一可選部分exception;
- sqlserver是@@error 或try catch final)
- 這個handler可以和多個條件關聯,類似於postgresql、oracle的when ... when ... when others...
- handler的sqlwarning 是 "01xxx"類的錯誤
- handler的not found 是 "02xxxx"類的錯誤
- handler的sqlexception 是 除了'00000'、'01xxxx'、"02xxxx"類的錯誤
- 注意sqlstate value ='00000' 或 mysql_error_code=0 表示操作成功,通常不應該去使用的!
- handler的continue表示當相關聯的塊的錯誤條件發生時、繼續從出錯的語句下一個語句執行;exit表示發生錯誤,立即終止程式的執行;undo目前尚未實現!
- 沒有handler的塊 或 定義了exit處理(不管是內層還是外層) 的程式 在錯誤發生時會終止程式的執行!
- 可以定義忽略任何錯誤的處理的空語句:declare continue handler for sqlwarning begin end;
遊標:唯讀、僅單步向前、不敏感的
declare cursor_name cursor for no_into_select_clause;
open cursor_name;
fetch cursor_name into var1 [,var2] [,...] ; 可能會產生 not found 異常錯誤
close cursor_name 如果沒有顯式調用關閉遊標的語句,遊標會在範圍超出定義該遊標的scope是自動銷毀
- mysql的cursor讀取沒有特殊的內部變數。利用handler 和 "not found"條件來處理
控制結構
if if_condition then
statement_list;
[elseif if_condition then statement_list;]
[elsestatement_list;]
end if;
case
when case_condition then statement_list;
[when case_condition then statement_list;]
[else statement_list;]
end case;
[repeat_label:] repeat --其他語言的do迴圈結構。
statement_list;
util repeat_condition
end repeat [repeat_label];
[while_label:] while while_condition do --其他語言的while迴圈結構
statement_list;
end while [while_label];
[loop_label:] loop --一般迴圈結構,注意沒有控制條件,必須在statement_list中含有控制條件、leave、iterate語句;
then statement_list;
end loop [loop_label];
leave label_name;
類似其他語言的exit [when..],跳出結構。用來退出begin..end、loop、repeat、while,前提是必須處於相應的結構裡,且結構定義了標籤
iterate label_name;
類似於其他語言的continue,繼續下次迴圈。用來退出loop、repeat、while,前提是必須處於相應的結構裡,且結構定義了標籤
函數的return exp; 語句 --僅僅用在儲存函數中的語句!