6Python全棧之路系列之MySQL存儲過程

Python全棧之路系列之MySQL存儲過程


存儲過程是一個SQL語句集合,當主動去調用存儲過程時,其中內部的SQL語句會按照邏輯執行。

存儲過程過接收的參數

參數描述
in僅用於傳入參數用
out僅用於返回值用
inout既可以傳入又可以當作返回值

創建存儲過程

創建一個簡單的存儲過程

-- 修改SQL語句的結束符爲%
delimiter %
-- 創建這個存儲過程先刪除
DROP PROCEDURE IF EXISTS proc_p1 %
CREATE PROCEDURE proc_p1()
-- 開始
BEGIN
    -- SQL語句塊
    select * from color;
-- 結束
END %
-- 把SQL語句的結束符改爲;
delimiter ;

通過call調用存儲過程

call proc_p1();

輸出爲

+-----+--------+
| nid | title  |
+-----+--------+
|   1 | red    |
|   2 | yellow |
+-----+--------+
2 rows in set (0.00 sec)
Query OK, 0 rows affected (0.01 sec)

刪除存儲過程

DROP PROCEDURE proc_p1;

實例

創建一個存儲過程,接收一個參數,傳入的參數就是顯示數據的個數,

delimiter %
DROP PROCEDURE IF EXISTS proc_p1 %
create PROCEDURE proc_p1(
    -- i1就是傳入的參數,傳入的數據類型必須是int類型
    in i1 int
)
BEGIN
    -- 定義兩個局部變量d1和d2,數據類型都爲int,d1默認值爲空,d2默認值爲1
    DECLARE d1 int;
    DECLARE d2 int DEFAULT 1;
    -- d1的值等於傳入過來的i1加上定義的局部變量d2的值
    SET d1 = i1 + d2;
    -- 查找person_info表中的nid大於d1的數據
    SELECT * FROM person_info WHERE nid > d1;
END %
delimiter ;

查詢,括號內輸入定義的參數

CALL proc_p1(4);

顯示結果

+-----+------+------------------+-------------+----------+----------+---------+-----------+
| nid | name | email            | phone       | part_nid | position | caption | color_nid |
+-----+------+------------------+-------------+----------+----------+---------+-----------+
|   6 | w    | [email protected] | 13800138000 |        5 | Python   | NULL    |      NULL |
|   9 | aa   | [email protected]     | 13800138000 |        3 | DBA      | NULL    |         2 |
|  10 | b    | b.ansheng.me     | 13800138000 |        3 | DBA      | NULL    |         1 |
+-----+------+------------------+-------------+----------+----------+---------+-----------+
3 rows in set (0.00 sec)

Query OK, 0 rows affected (0.01 sec)

這次把nid大於5的數據全部輸出出來了,傳入的值是4,我們在內部讓4+1了,所以就是大於5的數據.

delimiter %
DROP PROCEDURE IF EXISTS proc_p1 %
create PROCEDURE proc_p1(
    -- 接收了三個參數,類型都是int
    in i1 int,
    inout ii int,
    out i2 int
)
BEGIN
    -- 定義一個局部變量d2,默認值是3,數據類型爲int
    DECLARE d2 int DEFAULT 3;
    -- ii = ii + 1
    set ii = ii + 1;
    -- 如果傳入的i1等於1
    IF i1 = 1 THEN
        -- i2 = 100 + d2
        set i2 = 100 + d2;
    -- 如果傳入的i1等於2
    ELSEIF i1 = 2 THEN
        -- i2 = 200 + d2
        set i2 = 200 + d2;
    -- 否則
    ELSE
        -- i2 = 1000 + d2
        set i2 = 1000 + d2;
    END IF;
END %
delimiter ;

查看數據

set @o = 5;
CALL proc_p1(1,@o,@u);
SELECT @o,@u;

顯示的結果

+------+------+
| @o   | @u   |
+------+------+
|    6 |  103 |
+------+------+
1 row in set (0.00 sec)

使用pymysql模塊操作存儲過程

Python代碼爲:

import pymysql

conn = pymysql.connect(host="127.0.0.1", port=3306, user='root', passwd='as', db="dbname")
cursor = conn.cursor(cursor=pymysql.cursors.DictCursor)

# 執行存儲過程
row = cursor.callproc("proc_p2",(1,2,3))
# 存儲過程的查詢結果
selc = cursor.fetchall()
print(selc)
# 獲取存儲過程返回
effect_row = cursor.execute('select @_proc_p2_0, @_proc_p2_1, @_proc_p2_2')
# 取存儲過程返回值
result = cursor.fetchone()
print(result)

conn.commit()
cursor.close()
conn.close()

顯示的結果

C:\Python\Python35\python.exe D:/PycharmProjects/pymysql_存儲過程.py
[{'nid': 1, 'name': 'man1'}, {'nid': 2, 'name': 'man2'}, {'nid': 3, 'name': 'man3'}]
{'@_proc_p2_1': 3, '@_proc_p2_0': 1, '@_proc_p2_2': 103}

Process finished with exit code 0

存儲過程使用into

into其實就是把一個select的執行結果當作另一個select的參數,例如下面的實例:

delimiter %
DROP PROCEDURE IF EXISTS proc_p2 %
CREATE PROCEDURE proc_p2()
BEGIN
    -- 定義一個局部變量n,類型爲int
    DECLARE n int;
    -- 獲取color_nid = 2的數據並賦值給n
    SELECT color_nid into n FROM person_info where color_nid = 2;
    -- 輸出nid = n的數據
    SELECT * from color WHERE nid = n;
END %
delimiter ;

執行

call proc_p2();

結果

+-----+--------+
| nid | title  |
+-----+--------+
|   2 | yellow |
+-----+--------+
1 row in set (0.00 sec)

Query OK, 0 rows affected (0.01 sec)


#Python全棧之路

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章