MySQL的存儲函數(shù)(自定義函數(shù))和存儲過程都是用于存儲SQL語句的。但是什么時候用什么呢?是不是總是傻傻的分不清?
本文來詳細的講一下存儲函數(shù) 和存儲過程 ,以后再也不會迷糊。
一、 異同點
MySQL的存儲過程和函數(shù)都是一系列SQL語句的集合,調(diào)用時一次性執(zhí)行這些SQL語句。但是它們有一些不同之處:
- 存儲過程沒有返回值,而函數(shù)有一個返回值.
- 存儲過程可以在單個存儲過程中執(zhí)行一系列SQL語句,而自定義函數(shù)有諸多限制.
- 存儲過程可以返回多個值,而函數(shù)只能有一個返回值.
- 存儲過程實現(xiàn)較為復雜,自定義函數(shù)針對性強
- 存儲函數(shù)只能有輸入?yún)?shù),而且不能帶in, 而存儲過程可以有多個in,out,inout參數(shù)。
- 存儲過程可以調(diào)用存儲函數(shù)、但函數(shù)不能調(diào)用存儲過程。
名稱 | 創(chuàng)建 | 調(diào)用 | 返回 | 應用 |
---|---|---|---|---|
存儲函數(shù) | create function | select | 只能是一個 | 計算字段值、處理數(shù)據(jù)、觸發(fā)器(一般用于查詢結果為一個值并有返回結果的) |
存儲過程 | create procedure | call | 可以是多個也可以為空 | 1.復雜的業(yè)務邏輯,例如銀行轉(zhuǎn)賬、訂單處理;2.批量操作,例如批量插入、更新、刪除數(shù)據(jù);3.安全性控制,例如限制用戶訪問某些數(shù)據(jù)或執(zhí)行某些操作(一般用于更新) |
二、 存儲函數(shù)
存儲函數(shù)(自定義函數(shù))是一種對MySQL擴展的途徑,其用法與內(nèi)置的函數(shù)相同。
語法
創(chuàng)建
CREATE FUNCTION 函數(shù)名([func_parameter[…]])
RETURNS type
[characteristic …]
BEGIN
函數(shù)體
– sql語句
END
函數(shù)名:表示存儲函數(shù)的名稱;
func_parameter:表示存儲函數(shù)的參數(shù)列表,指定參數(shù)為IN、OUT或INOUT只對PROCEDURE是合法的,F(xiàn)UNCTION中總是默認為IN參數(shù)。
RETURNS type:語句表示函數(shù)返回數(shù)據(jù)的類型;
characteristic:創(chuàng)建函數(shù)時指定的對函數(shù)的約束。
func_parameter :由參數(shù)名稱和參數(shù)類型組成。
函數(shù)體:函數(shù)主體,包含函數(shù)邏輯和SQL語句.
示例:
delimiter $$
CREATE FUNCTION avg_salary(p_name VARCHAR(50))
RETURNS FLOAT
BEGIN
DECLARE avg_age FLOAT;
DECLARE total_salary FLOAT;
DECLARE num_employees INT;
DECLARE cur CURSOR FOR SELECT age FROM employees WHERE name = p_name;
DECLARE CONTINUE HANDLER FOR NOT FOUND SET num_employees = 0;
OPEN cur;
FETCH cur INTO avg_age;
CLOSE cur;
SELECT AVG(salary) INTO total_salary FROM employees WHERE name = p_name;
RETURN total_salary / avg_age;
end $$
delimiter ;
上述示例存儲函數(shù)接受一個參數(shù)p_name,表示要查詢的員工姓名。它首先聲明了三個變量:avg_age、total_salary和num_employees。然后,它使用游標遍歷employees表中與指定名稱匹配的所有行,并計算這些行中的平均年齡。最后,它返回總薪水除以平均年齡的結果。
> delimiter 是分隔符的意思 DELIMITER xx
> -- 示例:
> DELIMITER $$ -- 指定 $$ 為分隔符
> DELIMITER // -- 指定 // 為分隔符
> DELIMITER ; -- 指定 ; 為分隔符
調(diào)用
SELECT func_name()
調(diào)用函數(shù)名。
查看
查看定義: show create function func_name;
查看狀態(tài):show function status like ‘func_name’;
修改
ALTER FUNCTION function_name(parameters) [characteristic …];
刪除
DROP FUNCTION func_name
刪除函數(shù)的語法只需寫上函數(shù)名即可,函數(shù)的參數(shù)可以不用寫出來。
三、 存儲過程
存儲過程是一組為了完成特定功能的SQL語句集合,經(jīng)編譯后存儲在服務器端的數(shù)據(jù)庫中,利用存儲過程可以加速SQL語句的執(zhí)行
存儲過程的優(yōu)點是可以提高運行效率,且使用存儲過程的系統(tǒng)更加穩(wěn)定。
存儲過程的缺點是維護性較差,相對于簡單SQL,存儲過程的編寫和調(diào)試都比較困難。
語法
創(chuàng)建
存儲過程的創(chuàng)建步驟需要以下幾步:
- 聲明存儲過程的名稱和參數(shù)列表。
- 編寫存儲過程的主體部分,包括一系列SQL語句。
- 結束存儲過程的主體部分,并指定返回值類型。
- 調(diào)用存儲過程,傳遞參數(shù)并獲取返回結果。
create procedure 存儲過程名 ([params])
BEGIN
存儲過程體(一組合法的SQL語句)
END
參數(shù)列表(params):如果有多個參數(shù)則用逗號 , 分隔開,一個參數(shù)包括三部分:參數(shù)模式、參數(shù)名、參數(shù)類型,如:in name varchar(20)。參數(shù)模式有:in 輸入、out 輸出、inout 輸入輸出參數(shù)。
關于IN | OUT | INOUT的詳情如下:
IN :表示輸入?yún)?shù);它必須在調(diào)用存儲過程時指定,在存儲過程中修改該參數(shù)的值不能被返回,為默認值。僅需要將數(shù)據(jù)傳入存儲過程,并不需要返回計算后的該值。只能當做傳入?yún)?shù)
OUT: 表示輸出參數(shù);該值可在存儲過程內(nèi)部被改變,并可返回。不接受外部傳入的數(shù)據(jù),僅返回計算之后的值。只能當做轉(zhuǎn)出參數(shù)。也就是說,即使傳值給 OUT 參數(shù),該參數(shù)也無法得到你傳的值,得到的會是一個 null 值。
INOUT 表示既可以輸入也可以輸出;該參數(shù)即可作為輸入,又可做為輸出,也就是該參數(shù)既需要傳入值,又可以返回值。可當做傳入轉(zhuǎn)出參數(shù)
示例:
CREATE PROCEDURE GetEmployeeDetails(IN employeeID INT)
BEGIN
SELECT * FROM employees WHERE ID = employeeID;
END;
上述示例為一個名為GetEmployeeDetails的存儲過程,接受一個整型參數(shù)employeeID,用于查詢員工詳情。在存儲過程中,使用SELECT語句從employees表中查詢employeeID對應的記錄。最后,通過END關鍵字結束存儲過程的主體部分。
調(diào)用
使用 call 關鍵字來調(diào)用存儲過程
call func_name([ proc_parameter [,proc_parameter …]])
當無參數(shù)時,可以省略括號,不寫;
當有參數(shù)時,不可省略括號。
查看
查看定義: show create procedurefunc_name;
查看狀態(tài):show procedurestatus like ‘func_name’;
修改
alter procedure sp_name [characteristic …]
刪除
drop procedure sp_name;
其中characteristic的取值為:文章來源:http://www.zghlxwxcb.cn/news/detail-490515.html
值 | 說明 |
---|---|
language sql | 說明routine_body部分是由SQL語句組成的,當前系統(tǒng)支持的語言為SQL |
[not] deterministic | 指明存儲過程執(zhí)行的結果是否確定。DETERMINISTIC 表示結果是確定的。每次執(zhí)行存儲過程時,相同的輸入會得到相同的輸出。 |
{contains sql / no sql / reads sql data / modifies sql data} | 指明子程序使用SQL語句的限制。CONTAINS SQL表明子程序包含SQL語句,但是不包含讀寫數(shù)據(jù)的語句;NO SQL表明子程序不包含SQL語句;READS SQL DATA:說明子程序包含讀數(shù)據(jù)的語句;MODIFIES SQL DATA表明子程序包含寫數(shù)據(jù)的語句。默認情況下,系統(tǒng)會指定為CONTAINS SQL。 |
sql_security{definer/invoker} | 指明誰有權限來執(zhí)行。DEFINER 表示只有定義者才能執(zhí)行;INVOKER 表示擁有權限的調(diào)用者可以執(zhí)行。默認情況下,系統(tǒng)指定為DEFINER。 |
comment ‘string’ | 注釋信息,可以用來描述存儲過程或函數(shù) |
文章來源地址http://www.zghlxwxcb.cn/news/detail-490515.html
如果喜歡的話,歡迎 ??關注 ??點贊 ??評論 ??收藏 ??一起討論 你的評價就是我??創(chuàng)作的動力! ??????
到了這里,關于【Mysql 存儲過程 Or 存儲函數(shù) 傻傻分不清? 】的文章就介紹完了。如果您還想了解更多內(nèi)容,請在右上角搜索TOY模板網(wǎng)以前的文章或繼續(xù)瀏覽下面的相關文章,希望大家以后多多支持TOY模板網(wǎng)!