1. 程式人生 > 實用技巧 >【DataBase】MySQL 26 儲存過程

【DataBase】MySQL 26 儲存過程

一、概述

儲存過程&函式,類似程式語言的方法

什麼是方法?

完成特定功能的一組語句

方法的特點

1、可重用性

2、簡化操作

二、儲存過程【Stored Procedures】:

一組預先編譯好的SQL語句的集合,可理解批處理語句

提供給Java操作複雜的SQL邏輯將會變得困難

交給儲存過程將減少Java的邏輯複雜程度,減少編譯次數和資料庫服務的連線次數

提高SQL效率

適用場景:

大型系統專案

三、語法和使用

1、總體語法:

CREATE PROCEDURE 儲存過程識別符號(引數列表)

BEGIN (開始過程)

# 儲存過程【一組符合語法的SQL語句】

END (結束過程)

2、引數的寫法:

引數模式 引數名稱 引數型別

樣例:

IN aaa VARCHAR(24)

3、引數模式的種類:

IN  
# 僅輸入,需要呼叫方法傳入值

OUT
# 僅輸出,可以作為儲存過程的返回值,等同Java的返回型別宣告

INOUT
# 兼輸入輸出

4、語法事項:

1、如果儲存過程只有一句SQL語句需要執行,可以不寫BEGIN & END

2、每條SQL語句的結尾必須協商分號

3、儲存過程的結尾關鍵字可以使用DELIMTER關鍵字重新設定

5、DELIMITER使用

DELIMITER 結束標記

6、儲存過程的呼叫語法

CALL 儲存過程名稱(實際引數);

四、三種引數模式的案例:

無參儲存過程

建立一個儲存過程

DELIMITER $

CREATE PROCEDURE batchInsert()
BEGIN
    INSERT INTO 
        admin(`username`,`password`) 
    VALUES
        ('john','3333'),
        ('rose','4444'),
        ('jack','5555'),
        ('tomy','6666'),
        ('jerry','7777');
END $

建立完成之後會保留在資料庫中

呼叫儲存過程:

在案例中需要使用$在儲存過程的結尾寫上

但是發現報錯:

錯誤程式碼: 1064
You have an error in your SQL syntax; 
check the manual that corresponds to your MySQL server version for the right syntax to use near '$' at line 1

SQL語法檢查發現不需要新增$,執行成功

CALL batchInsert()

帶IN模式引數的儲存過程

報錯發現每次必須要宣告 結尾標識

這個結尾標識必須緊跟END

DELIMITER $
CREATE PROCEDURE queryBoyInfoByGirlName(IN beautyName VARCHAR(20))
BEGIN
    SELECT 
        bo.*
    FROM
        boys bo RIGHT JOIN beauty b ON bo.id = b.boyfriend_id
    WHERE 
        b.name = beautyName;
END$

儲存過程呼叫:

CALL `queryBoyInfoByGirlName`('熱巴')

多IN模式引數儲存過程:

DELIMITER $
CREATE PROCEDURE login
(
IN `username` VARCHAR(20),
IN `password` VARCHAR(20)
)
BEGIN
	DECLARE result VARCHAR(20) DEFAULT '';
	# ------------------------------------------
	SELECT 
		COUNT(*)
	INTO 
		result
	FROM
		admin
	WHERE
		admin.`username` = `username`
		AND
		admin.`password` = `password`;
	# ------------------------------------------
	SELECT result;
END $

儲存過程呼叫:

CALL login('john', '8888');

如果還需要顯示成功或者失敗字元

DELIMITER $
CREATE PROCEDURE login2
(
IN `username` VARCHAR(20),
IN `password` VARCHAR(20)
)
BEGIN
	DECLARE result VARCHAR(20) DEFAULT 0;
	# ------------------------------------------
	SELECT 
		COUNT(*)
	INTO 
		result
	FROM
		admin
	WHERE
		admin.`username` = `username`
		AND
		admin.`password` = `password`;
	# ------------------------------------------
	SELECT IF(result > 0, '登入成功', '登入失敗') AS '提示資訊';
END $

帶Out模式引數的儲存過程

DELIMITER $
CREATE PROCEDURE queryGirlNameByBoy
(
IN beautyName VARCHAR(20), 
OUT boyName VARCHAR(20)
)
BEGIN
	SELECT 
		boys.`boyName`
	INTO 
		boyName
	FROM 
		boys INNER JOIN beauty ON boys.id = beauty.`boyfriend_id`
	WHERE 
		beauty.`name` = beautyName;
END $

呼叫時注入一個變數,由變數查詢返回

CALL queryGirlNameByBoy('小昭', @bName);
SELECT @bName AS '名稱'

除了名字以外,再追加一個CP欄位值,重寫儲存過程

DELIMITER $
CREATE PROCEDURE queryBoyNameAndCpValueByGirlName
(
IN beautyName VARCHAR(20), 
OUT boyName VARCHAR(20),
OUT coupleValue INT
)
BEGIN
	SELECT 
		boys.`boyName`, boys.`userCP`
	INTO 
		boyName, coupleValue
	FROM 
		boys INNER JOIN beauty ON boys.id = beauty.`boyfriend_id`
	WHERE 
		beauty.`name` = beautyName;
END $

呼叫:

CALL queryBoyNameAndCpValueByGirlName
(
'小昭',
@bName,
@userCP
);
SELECT @bName 'NAME', @userCP 'CoupleValue';

帶INOUT模式引數的儲存過程:

DELIMITER $
CREATE PROCEDURE returnDouble
(
INOUT a INT,
INOUT b INT
)
BEGIN
	SET a = a * 2;
	SET b = b * 2;
END$

呼叫:

SET @varA = 125;
SET @varB = 334;

CALL returnDouble(@varA, @varB);
SELECT @varA, @varB;

五、儲存過程的刪除和檢視

在之前的案例中我們已經建立了許多儲存過程

刪除語法:

DROP PROCEDURE 儲存過程名稱

刪除語句一次只能刪除一個,不可以實現多個刪除

檢視語法:

SHOW CREATE PROCEDURE 儲存過程名稱

六、為什麼沒有儲存過程修改?

儲存過程是由修改的SQL的,但是能夠修改的只有特定的元資料

不能對儲存過程的邏輯進行修改,改了沒改都一樣,沒有太大的意義

詳細資料參見:

https://www.cnblogs.com/geaozhang/p/6817698.html

如果要實現我們的真正意義上的修改,就需要先刪除儲存過程,再重新建立