激情久久久_欧美视频区_成人av免费_不卡视频一二三区_欧美精品在欧美一区二区少妇_欧美一区二区三区的

服務器之家:專注于服務器技術及軟件下載分享
分類導航

Mysql|Sql Server|Oracle|Redis|MongoDB|PostgreSQL|Sqlite|DB2|mariadb|Access|數據庫技術|

服務器之家 - 數據庫 - Mysql - MySQL分頁優化

MySQL分頁優化

2020-06-05 19:51iVictor Mysql

這篇文章主要為大家詳細介紹了MySQL分頁優化,內容思路很詳細,有意對MySQL分頁優化的朋友可以參考一下

最近,幫同事重寫了一個MySQL SQL語句,該SQL語句涉及兩張表,其中一張表是字典表(需返回一個字段),另一張表是業務表(本身就有150個字段,需全部返回),當然,字段的個數是否合理在這里不予評價。平時,返回的數據大概5w左右,系統尚能收到數據。但12月31日那天,數據量大概20w,導致SQL執行時間過長,未能在規定的時間內反饋結果,于是系統直接報錯。

一般的思路是用MySQL的分頁功能,即直接在原SQL語句后面增加LIMIT子句。但請注意,雖然你看到的反饋結果只是LIMIT后面指定的數量,于是想當然的以為MySQL只是檢索了指定數量的數據,然后給予返回。其實,MySQL內部實現的原理是,檢索所有符合where條件的記錄,然后返回指定數量的記錄。從這個角度來看,直接在原SQL語句后面添加LIMIT子句只能說是一種可以實現功能的方案,但未必最優。

具體在本例中,首先我們來看一下150個字段的表的統計信息:

MySQL分頁優化

一行大概就占2k,而Innodb默認頁的大小為16k,這意味著,一個頁中最多可存儲8行的數據。隨機讀的可能性大大增加。而這無疑會對數據庫系統的IO造成極大的壓力。 

優化前

如果采用上述方案,即直接在原SQL語句后面增加LIMIT子句,下面,我們來看看它的執行情況。

首先,直接添加LIMIT子句后的SQL語句如下(已省略a1表的150個字段和a2中的一個字段):

 

復制代碼 代碼如下:
FROM upay_csys_scquery_txn_log_his a1  LEFT JOIN upay_csys_trans_code a2 on(a1.int_trans_code=a2.trans_code) WHERE STATUS<>'00' AND settle_date=20151230 limit 50000,10000;


其執行時間如下:

MySQL分頁優化

大概執行了32s,絕大部分都花費到Sending data上了。Sending data指的是服務器檢索數據,讀取數據,并將數據返回給客戶端的時間。

關于上述執行結果,有以下幾點需要說明:

1. 這是SQL語句多次執行后的結果,這樣就可以排除結果緩存的影響,事實上,每次查詢的時長都是32s左右。

2. 為什么選用的是limit 50000,10000,而不是0,10000,這個主要是考慮到對于LIMIT子句來說,越到后面,分頁的成本越高。基于此,選擇了中間值來作為分頁的結果。

該語句的執行計劃如下:

MySQL分頁優化

優化后:

優化的思路:

只對該表的主鍵進行分頁,然后用返回的主鍵作為子查詢的結果,來檢索該表其它字段的值。

改寫后的SQL語句如下:

 

復制代碼 代碼如下:
FROM upay_csys_scquery_txn_log_his a1  LEFT JOIN upay_csys_trans_code a2 on(a1.int_trans_code=a2.trans_code) where seq_id in (select seq_id from (select seq_id FROM upay_csys_scquery_txn_log_his a1  WHERE STATUS<>'00' AND settle_date=20151230 order by 1 limit 50000,10000) as t);


其執行時間如下:

MySQL分頁優化

大概3s多,比第一種方案快了差不多10倍,效果顯著。

下面來看看其執行計劃(explain extended)

MySQL分頁優化

 總結:

1. 改寫后的語句原本如下:

 

復制代碼 代碼如下:
FROM upay_csys_scquery_txn_log_his a1  LEFT JOIN upay_csys_trans_code a2 on(a1.int_trans_code=a2.trans_code) where seq_id in (select seq_id FROM upay_csys_scquery_txn_log_his a1  WHERE STATUS<>'00' AND settle_date=20151230 order by 1 limit 50000,10000);


但MySQL報以下錯誤:

 

復制代碼 代碼如下:
ERROR 1235 (42000): This version of MySQL doesn't yet support 'LIMIT & IN/ALL/ANY/SOME subquery'


需再增加一個嵌套子查詢,

比如這樣的語句是不能正確執行的。

復制代碼 代碼如下:
select * from table where id in (select id from table limit 12);

但是,只要你再加一層就行。如:

復制代碼 代碼如下:
select * from table where id in (select t.id from (select * from table limit 12)as t)

這樣就可以繞開limit子查詢的問題。
問題解決。

2. 如果想查看MySQL查詢優化器等價改寫后的SQL語句,可首先通過explain extended得到具體的執行計劃,然后通過show warnings查看。

具體在本例中,等價改寫后的SQL語句如下:

MySQL分頁優化

與設想中的執行順序一致~

3. 如何查看MySQL語句各步驟的執行時間。

以上就是本文的全部內容,希望對大家MySQL分頁優化有所幫助。

延伸 · 閱讀

精彩推薦
主站蜘蛛池模板: 国产高清美女一级毛片 | 1级黄色毛片 | 12av毛片 | 欧美成在线视频 | 免费特黄 | 久久一区三区 | 久久久aa | 蜜桃91丨九色丨蝌蚪91桃色 | av影院在线播放 | 污片视频在线观看 | 91网站永久免费看 | 黄色成人小视频 | 久久精品日产第一区二区三区 | 91热久久免费频精品黑人99 | 国产午夜精品一区二区三区四区 | 午色影院| 久久毛片免费 | 久久久久国产成人免费精品免费 | 国产精品剧情一区二区在线观看 | 性欧美一区二区 | 国产分类视频 | 免费在线观看毛片 | 欧美精品日日鲁夜夜添 | 国产精品免费一区二区三区都可以 | 久久国产精品久久精品国产演员表 | 一本色道久久99精品综合蜜臀 | 久久精品一区视频 | 13一14毛片免费看 | 妇女毛片| 2021免费日韩视频网 | 日本免费aaa观看 | 成人免费精品视频 | 国产精品一区网站 | 一区二区高清视频在线观看 | wwwxxx免费视频| 成人爱情偷拍视频在线观看 | 日韩在线观看中文字幕 | 欧美高清另类自拍视频在线看 | 9999视频 | 中文字幕一区在线观看视频 | 亚欧美一区二区 |