最新国产好看的视频,伊人天堂AV在线,国产Aaaaaa视频,蜜臀视频在线观看一区,人妻av色图,密臀久久久精品影片,青青视频免费观看毛片,久草在线观看视,国产三级精品色情在线

MySQL?SQL預(yù)處理(Prepared)的語法實例與注意事項

 更新時間:2022年01月09日 11:50:22   作者:GeaoZhang  
所謂預(yù)編譯語句就是將此類SQL語句中的值用占位符替代,可以視為將 SQL語句模板化或者說參數(shù)化,一般稱這類語句叫Prepared Statements,下面這篇文章主要給大家介紹了關(guān)于MySQL?SQL預(yù)處理(Prepared)的相關(guān)資料,需要的朋友可以參考下

一、SQL 語句的執(zhí)行處理

1、即時 SQL

一條 SQL 在 DB 接收到最終執(zhí)行完畢返回,大致的過程如下:

  1. 詞法和語義解析;

  2. 優(yōu)化 SQL 語句,制定執(zhí)行計劃;

  3. 執(zhí)行并返回結(jié)果;

如上,一條 SQL 直接是走流程處理,一次編譯,單次運(yùn)行,此類普通語句被稱作 Immediate Statements (即時 SQL)。

2、預(yù)處理 SQL

但是,絕大多數(shù)情況下,某需求某一條 SQL 語句可能會被反復(fù)調(diào)用執(zhí)行,或者每次執(zhí)行的時候只有個別的值不同(比如 select 的 where 子句值不同,update 的 set 子句值不同,insert 的 values 值不同)。如果每次都需要經(jīng)過上面的詞法語義解析、語句優(yōu)化、制定執(zhí)行計劃等,則效率就明顯不行了。

所謂預(yù)編譯語句就是將此類 SQL 語句中的值用占位符替代,可以視為將 SQL 語句模板化或者說參數(shù)化,一般稱這類語句叫Prepared Statements。

預(yù)編譯語句的優(yōu)勢在于歸納為:一次編譯、多次運(yùn)行,省去了解析優(yōu)化等過程;此外預(yù)編譯語句能防止 SQL 注入。

注意:

雖然可能是通過預(yù)處理 SQL 的方式一定程度的提高了效率,但是對于優(yōu)化而言,最優(yōu)的執(zhí)行計劃不是光靠 SQL 語句的模板化來實現(xiàn)的,往往還是需要通過具體值來預(yù)估出成本代價。

二、Prepared SQL Statement Syntax

MySQL 官方將 prepare、execute、deallocate 統(tǒng)稱為 PREPARE STATEMENT。翻譯也就習(xí)慣的稱其為預(yù)處理語句。

MySQL 預(yù)處理語句的支持版本較早,所以我們目前普遍使用的 MySQL 版本都是支持這一語法的。

語法:

# 定義預(yù)處理語句
PREPARE stmt_name FROM preparable_stmt;
# 執(zhí)行預(yù)處理語句
EXECUTE stmt_name [USING @var_name [, @var_name] ...];
# 刪除(釋放)定義
{DEALLOCATE | DROP} PREPARE stmt_name;

 1、利用字符串定義預(yù)處理 SQL (直角三角形計算)

mysql> PREPARE stmt1 FROM 'SELECT SQRT(POW(?,2) + POW(?,2)) AS hypotenuse';
Query OK, 0 rows affected (0.00 sec)
Statement prepared

mysql> SET @a = 3;
Query OK, 0 rows affected (0.00 sec)

mysql> SET @b = 4;                                                   
Query OK, 0 rows affected (0.00 sec)

mysql> EXECUTE stmt1 USING @a, @b;
+------------+
| hypotenuse |
+------------+
|          5 |
+------------+
1 row in set (0.00 sec)

mysql> DEALLOCATE PREPARE stmt1;                                     
Query OK, 0 rows affected (0.00 sec)

 2、利用變量定義預(yù)處理 SQL (直角三角形計算)

mysql> SET @s = 'SELECT SQRT(POW(?,2) + POW(?,2)) AS hypotenuse';
Query OK, 0 rows affected (0.00 sec)

mysql> PREPARE stmt2 FROM @s;
Query OK, 0 rows affected (0.00 sec)
Statement prepared

mysql> SET @c = 6;
Query OK, 0 rows affected (0.00 sec)

mysql> SET @d = 8;
Query OK, 0 rows affected (0.00 sec)

mysql> EXECUTE stmt2 USING @c, @d;
+------------+
| hypotenuse |
+------------+
|         10 |
+------------+
1 row in set (0.00 sec)

mysql> DEALLOCATE PREPARE stmt2;
Query OK, 0 rows affected (0.00 sec)

 3、解決無法傳參問題

我們知道,對于 LIMIT 子句中的值,必須是常量,不得使用變量,也就是說不能使用:SELECT * FROM TABLE LIMIT @skip, @numrows; 如此,就可以是用 PREPARE 語句解決此問題。

mysql> SET @skip = 100; SET @numrows = 3;
Query OK, 0 rows affected (0.00 sec)

Query OK, 0 rows affected (0.00 sec)

mysql> SELECT * FROM t1 LIMIT @skip, @numrows;
ERROR 1064 (42000): 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 '@skip, @numrows' at line 1

mysql> PREPARE stmt3 FROM "SELECT * FROM t1 LIMIT ?, ?";
Query OK, 0 rows affected (0.00 sec)
Statement prepared

mysql> EXECUTE stmt3 USING @skip, @numrows;
+-----+--------+
| a   | filler |
+-----+--------+
| 100 | filler |
| 101 | filler |
| 102 | filler |
+-----+--------+
3 rows in set (0.00 sec)

mysql> DEALLOCATE PREPARE stmt3;
Query OK, 0 rows affected (0.00 sec)

如此一來,結(jié)合2中介紹的利用變量定義預(yù)處理 SQL 也就基本解決了傳參時語法報錯問題了,類似的:用變量傳參做表名時,MySQL 會把變量名當(dāng)做表名,這樣既不是本意,也會是語法錯誤,在 SQL Server 的解決辦法是利用字符串拼接穿插變量進(jìn)行傳參,再將整條 SQL 語句作為變量,最后是用 sp_executesql 調(diào)用該拼接 SQL 執(zhí)行,而 Prepared SQL Statement 可謂異曲同工之妙。

mysql> SET @table = 't2';
Query OK, 0 rows affected (0.00 sec)

mysql> SET @s = CONCAT('SELECT * FROM ', @table);
Query OK, 0 rows affected (0.00 sec)

mysql> PREPARE stmt4 FROM @s;
Query OK, 0 rows affected (0.00 sec)
Statement prepared

mysql> EXECUTE stmt4;
+------+-------+-------+
| id   | score | grade |
+------+-------+-------+
|    1 |    99 | A     |
|    2 |    81 | B     |
|    3 |    55 | D     |
|    4 |    69 | C     |
+------+-------+-------+
4 rows in set (0.00 sec)

mysql> DROP PREPARE stmt4;
Query OK, 0 rows affected (0.00 sec)

三、預(yù)處理 SQL 使用注意點

1、stmt_name 作為 preparable_stmt 的接收者,唯一標(biāo)識,不區(qū)分大小寫。

2、preparable_stmt 語句中的 ? 是個占位符,所代表的是一個字符串,不需要將 ? 用引號包含起來。

3、定義一個已存在的 stmt_name ,原有的將被立即釋放,類似于變量的重新賦值。

4、PREPARE stmt_name 的作用域是session級

可以通過 max_prepared_stmt_count 變量來控制全局最大的存儲的預(yù)處理語句。

mysql> show variables like 'max_prepared%';
+-------------------------+-------+
| Variable_name           | Value |
+-------------------------+-------+
| max_prepared_stmt_count | 16382 |
+-------------------------+-------+
1 row in set (0.00 sec)

預(yù)處理編譯 SQL 是占用資源的,所以在使用后注意及時使用 DEALLOCATE PREPARE 釋放資源,這是一個好習(xí)慣。

四、Prepared Statements優(yōu)點

1.安全

Prepared Statements通過sql邏輯與數(shù)據(jù)的分離來增加安全,sql邏輯與數(shù)據(jù)的分離能防止普通類型的sql注入攻擊(SQL injection attack)。

2.性能

Prepared Statements只語法分析一次,你初始話Prepared Statements時,mysql將檢查語法并準(zhǔn)備語句的運(yùn)行,當(dāng)你執(zhí)行query 多次時,這樣就不會在有額外的負(fù)擔(dān)了,如果,當(dāng)運(yùn)行query 很多次的時候(如:insert)這種預(yù)處理有很大的性能提高

他使用binary protocol協(xié)議,這樣更能提高效率。

總結(jié)

到此這篇關(guān)于MySQL SQL預(yù)處理(Prepared)的文章就介紹到這了,更多相關(guān)MySQL SQL預(yù)處理(Prepared)內(nèi)容請搜索腳本之家以前的文章或繼續(xù)瀏覽下面的相關(guān)文章希望大家以后多多支持腳本之家!

相關(guān)文章

  • IDEA使用mybatis-generator及配上mysql8.0.3版本遇到的bug

    IDEA使用mybatis-generator及配上mysql8.0.3版本遇到的bug

    這篇文章主要介紹了IDEA使用mybatis-generator以及配上mysql8.0.3版本遇到的問題,本文通過實例代碼給大家介紹的非常詳細(xì),對大家的學(xué)習(xí)或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2020-11-11
  • MySQL中的存儲過程異常處理

    MySQL中的存儲過程異常處理

    這篇文章主要介紹了MySQL中的存儲過程異常處理方式,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-09-09
  • 詳解Mysql查詢條件中字符串尾部有空格也能匹配上的問題

    詳解Mysql查詢條件中字符串尾部有空格也能匹配上的問題

    在本篇文章里小編給大家整理的是關(guān)于詳解Mysql查詢條件中字符串尾部有空格也能匹配上的問題,需要的朋友們可以參考下
    2020-02-02
  • SQL字符串以及數(shù)字常用操作匯總

    SQL字符串以及數(shù)字常用操作匯總

    本篇文章是對SQL字符串以及數(shù)字的常用操作進(jìn)行了詳細(xì)的總結(jié)與分析,需要的朋友參考下
    2013-06-06
  • ERROR: Error in Log_event::read_log_event()

    ERROR: Error in Log_event::read_log_event()

    ERROR: Error in Log_event::read_log_event(): read error, data_len: 438, event_type: 2
    2014-02-02
  • windows下安裝mysql8.0.18的教程(社區(qū)版)

    windows下安裝mysql8.0.18的教程(社區(qū)版)

    本文章簡單介紹一下mysql在windows下的安裝方式,主要介紹了mysql社區(qū)版8.0.18版本,本文給大家介紹的非常詳細(xì),需要的朋友參考下吧
    2020-01-01
  • MySQL表鎖、頁面鎖和行鎖的作用及其優(yōu)缺點對比分析

    MySQL表鎖、頁面鎖和行鎖的作用及其優(yōu)缺點對比分析

    MySQL中的表鎖、頁面鎖和行鎖各有特點,適用于不同的場景,表鎖鎖定整個表,適用于批量操作和MyISAM存儲引擎,頁面鎖鎖定數(shù)據(jù)頁,適用于舊版本InnoDB,行鎖僅鎖定某一行,適用于高并發(fā)事務(wù),選擇合適的鎖機(jī)制可以顯著提升MySQL的并發(fā)性能和數(shù)據(jù)一致性,感興趣的朋友一起學(xué)習(xí)吧
    2025-03-03
  • Navicat Premium如何導(dǎo)入SQL文件的方法步驟

    Navicat Premium如何導(dǎo)入SQL文件的方法步驟

    這篇文章主要介紹了Navicat Premium如何導(dǎo)入SQL文件的方法步驟,文中通過示例代碼介紹的非常詳細(xì),對大家的學(xué)習(xí)或者工作具有一定的參考學(xué)習(xí)價值,需要的朋友們下面隨著小編來一起學(xué)習(xí)學(xué)習(xí)吧
    2021-03-03
  • MySQL讀寫分離服務(wù)配置方式

    MySQL讀寫分離服務(wù)配置方式

    通過Mycat代理實現(xiàn)MySQL的讀寫分離涉及準(zhǔn)備工作、配置文件修改、權(quán)限設(shè)置、啟動方式選擇等關(guān)鍵步驟,首先,安裝JDK1.8并配置環(huán)境變量;接著,對Mycat的server.xml和schema.xml進(jìn)行配置,特別是schema.xml中對數(shù)據(jù)庫的配置需關(guān)注
    2024-11-11
  • Mysql數(shù)據(jù)庫連接失敗SSLException: Unsupported record version Unknown-0.0問題

    Mysql數(shù)據(jù)庫連接失敗SSLException: Unsupported record 

    這篇文章主要介紹了Mysql數(shù)據(jù)庫連接失敗SSLException: Unsupported record version Unknown-0.0問題,具有很好的參考價值,希望對大家有所幫助,如有錯誤或未考慮完全的地方,望不吝賜教
    2024-06-06

最新評論

大名县| 确山县| 瓦房店市| 邹平县| 璧山县| 关岭| 临江市| 日喀则市| 洱源县| 景德镇市| 泽库县| 富顺县| 大港区| 侯马市| 登封市| 二连浩特市| 西充县| 武城县| 和田县| 寻甸| 隆回县| 苍梧县| 东城区| 漠河县| 连城县| 岳池县| 牡丹江市| 锡林郭勒盟| 巴彦县| 竹溪县| 农安县| 酒泉市| 嫩江县| 讷河市| 乐至县| 平谷区| 襄城县| 山阳县| 浮山县| 吴桥县| 衡南县|