線上千萬級大表排序該如何優(yōu)化?

image

前言

??前段時間應(yīng)急群有客服反饋带到,會員管理功能無法按到店時間昧碉、到店次數(shù)、消費(fèi)金額 進(jìn)行排序揽惹。經(jīng)過排查發(fā)現(xiàn)是Sql執(zhí)行效率低被饿,并且索引效率低下。遇到這樣的情況我們該如何處理呢搪搏?今天我們聊一聊Mysql大表查詢優(yōu)化狭握。

應(yīng)急問題

??商戶反饋會員管理功能無法按到店時間、到店次數(shù)疯溺、消費(fèi)金額 進(jìn)行排序论颅,一直轉(zhuǎn)圈圈或轉(zhuǎn)完無變化哎垦,商戶要以此數(shù)據(jù)來做活動,比較著急恃疯,請盡快處理漏设,謝謝。

線上數(shù)據(jù)量

merchant_member_info 7000W條數(shù)據(jù)今妄。

member_info 3000W郑口。

不要問我為什么不分表,改動太大蛙奖,無能為力潘酗。

問題SQL如下


SELECT

mui.id,

mui.merchant_id,

mui.member_id,

DATE_FORMAT(

mui.recently_consume_time,

'%Y%m%d%H%i%s'

) recently_consume_time,

IFNULL(mui.total_consume_num, 0) total_consume_num,

IFNULL(mui.total_consume_amount, 0) total_consume_amount,

(

CASE

WHEN u.nick_name IS NULL THEN

'會員'

WHEN u.nick_name = '' THEN

'會員'

ELSE

u.nick_name

END

) AS 'nickname',

u.sex,

u.head_image_url,

u.province,

u.city,

u.country

FROM

merchant_member_info mui

LEFT JOIN member_info u ON mui.member_id = u.id

WHERE

1 = 1

AND mui.merchant_id = '商戶編號'

ORDER BY

mui.recently_consume_time DESC / ASC

LIMIT 0,

10

出現(xiàn)的原因

??經(jīng)過驗(yàn)證可以按照“到店時間”進(jìn)行降序排序,但是無法按照升序進(jìn)行排序主要是查詢太慢了雁仲。主要原因是:雖然該查詢使用建立了recently_consume_time索引,但是索引效率低下琐脏,需要查詢整個索引樹攒砖,導(dǎo)致查詢時間過長。

DESC 查詢大概需要4s日裙,ASC 查詢太慢耗時未知吹艇。

為什么降序排序快和而升序慢呢?

image

??因?yàn)槭菍r間建立了索引昂拂,最近的時間一定在最后面受神,升序查詢,需要查詢更多的數(shù)據(jù)格侯,才能過濾出相應(yīng)的結(jié)果鼻听,所以慢。

解決方案

目前生產(chǎn)庫的索引

image

調(diào)整索引

??需要刪除index_merchant_user_last_time索引联四,同時將index_merchant_user_merchant_ids單例索引撑碴,變?yōu)?merchant_id,recently_consume_time組合索引。

調(diào)整結(jié)果(準(zhǔn)生產(chǎn))

image

調(diào)整前后結(jié)果對比(準(zhǔn)生產(chǎn))

?測試數(shù)據(jù)

?merchant_member_info 有902606條記錄朝墩。

?member_info 表有775條記錄醉拓。

SQL執(zhí)行效率

優(yōu)化前

image

優(yōu)化后

image

type由index -> ref

ref由 null -> const

| TOP | 優(yōu)化前 | 優(yōu)化后 |

| ------------- | ------- | ------ |

| 到店時間-降序 | 0.274s | 0.003s |

| 到店時間-升序 | 11.245s | 0.003s |

調(diào)整索引需要執(zhí)行的SQL


執(zhí)行的注意事項:

由于表中的數(shù)據(jù)量太大裳朋,請在晚上進(jìn)行執(zhí)行污呼,并且需要分開執(zhí)行末早。

# 刪除近期消費(fèi)時間索引

ALTER TABLE merchant_member_info DROP INDEX index_merchant_user_last_time;

# 刪除商戶編號索引

ALTER TABLE merchant_member_info DROP INDEX index_merchant_user_merchant_ids;

# 建立商戶編號和近期消費(fèi)時間組合索引

ALTER TABLE merchant_member_info ADD INDEX idx_merchant_id_recently_time (`merchant_id`,`recently_consume_time`);

經(jīng)詢問敬扛,重建索引花了30分鐘司澎。

最終的分頁查詢優(yōu)化

??上面的sql雖然經(jīng)過調(diào)整索引柄延,雖然能達(dá)到較高的執(zhí)行效率众眨,但是隨著分頁數(shù)據(jù)的不斷增加碌嘀,性能會急劇下降杜跷。

| 分頁數(shù)據(jù) | 查詢時間 | 優(yōu)化后 |

| ------------- | -------- | ------ |

| limit 0,10 | 0.003s | 0.002s |

| limit 10,10 | 0.005s | 0.002s |

| limit 100,10 | 0.009s | 0.002s |

| limit 1000,10 | 0.044s | 0.004s |

| limit 9000,10 | 0.247s | 0.016s |

最終的sql

?優(yōu)化思路:先走覆蓋索引定位到傍念,需要的數(shù)據(jù)行的主鍵值矫夷,然后INNER JOIN 回原表,取到其他數(shù)據(jù)憋槐。


SELECT

mui.id,

mui.merchant_id,

mui.member_id,

DATE_FORMAT(

mui.recently_consume_time,

'%Y%m%d%H%i%s'

) recently_consume_time,

IFNULL(mui.total_consume_num, 0) total_consume_num,

IFNULL(mui.total_consume_amount, 0) total_consume_amount,

(

CASE

WHEN u.nick_name IS NULL THEN

'會員'

WHEN u.nick_name = '' THEN

'會員'

ELSE

u.nick_name

END

) AS 'nickname',

u.sex,

u.head_image_url,

u.province,

u.city,

u.country

FROM

merchant_member_info mui

INNER JOIN (

SELECT

id

FROM

merchant_member_info

WHERE

merchant_id = '商戶ID'

ORDER BY

recently_consume_time DESC

LIMIT 9000,

10

) AS tmp ON tmp.id = mui.id

LEFT JOIN member_info u ON mui.member_id = u.id

結(jié)尾

??如果覺得對你有幫助双藕,可以多多評論,多多點(diǎn)贊哦阳仔,也可以到我的主頁看看忧陪,說不定有你喜歡的文章,也可以隨手點(diǎn)個關(guān)注哦近范,謝謝嘶摊。

??我是不一樣的科技宅,每天進(jìn)步一點(diǎn)點(diǎn)评矩,體驗(yàn)不一樣的生活叶堆。我們下期見!

?著作權(quán)歸作者所有,轉(zhuǎn)載或內(nèi)容合作請聯(lián)系作者
  • 序言:七十年代末斥杜,一起剝皮案震驚了整個濱河市虱颗,隨后出現(xiàn)的幾起案子,更是在濱河造成了極大的恐慌蔗喂,老刑警劉巖忘渔,帶你破解...
    沈念sama閱讀 219,110評論 6 508
  • 序言:濱河連續(xù)發(fā)生了三起死亡事件,死亡現(xiàn)場離奇詭異缰儿,居然都是意外死亡畦粮,警方通過查閱死者的電腦和手機(jī),發(fā)現(xiàn)死者居然都...
    沈念sama閱讀 93,443評論 3 395
  • 文/潘曉璐 我一進(jìn)店門乖阵,熙熙樓的掌柜王于貴愁眉苦臉地迎上來宣赔,“玉大人,你說我怎么就攤上這事义起±常” “怎么了?”我有些...
    開封第一講書人閱讀 165,474評論 0 356
  • 文/不壞的土叔 我叫張陵默终,是天一觀的道長椅棺。 經(jīng)常有香客問我,道長齐蔽,這世上最難降的妖魔是什么两疚? 我笑而不...
    開封第一講書人閱讀 58,881評論 1 295
  • 正文 為了忘掉前任,我火速辦了婚禮含滴,結(jié)果婚禮上诱渤,老公的妹妹穿的比我還像新娘。我一直安慰自己谈况,他們只是感情好勺美,可當(dāng)我...
    茶點(diǎn)故事閱讀 67,902評論 6 392
  • 文/花漫 我一把揭開白布递胧。 她就那樣靜靜地躺著,像睡著了一般赡茸。 火紅的嫁衣襯著肌膚如雪缎脾。 梳的紋絲不亂的頭發(fā)上,一...
    開封第一講書人閱讀 51,698評論 1 305
  • 那天占卧,我揣著相機(jī)與錄音遗菠,去河邊找鬼。 笑死华蜒,一個胖子當(dāng)著我的面吹牛辙纬,可吹牛的內(nèi)容都是我干的。 我是一名探鬼主播叭喜,決...
    沈念sama閱讀 40,418評論 3 419
  • 文/蒼蘭香墨 我猛地睜開眼贺拣,長吁一口氣:“原來是場噩夢啊……” “哼!你這毒婦竟也來了捂蕴?” 一聲冷哼從身側(cè)響起纵柿,我...
    開封第一講書人閱讀 39,332評論 0 276
  • 序言:老撾萬榮一對情侶失蹤,失蹤者是張志新(化名)和其女友劉穎启绰,沒想到半個月后,有當(dāng)?shù)厝嗽跇淞掷锇l(fā)現(xiàn)了一具尸體沟使,經(jīng)...
    沈念sama閱讀 45,796評論 1 316
  • 正文 獨(dú)居荒郊野嶺守林人離奇死亡委可,尸身上長有42處帶血的膿包…… 初始之章·張勛 以下內(nèi)容為張勛視角 年9月15日...
    茶點(diǎn)故事閱讀 37,968評論 3 337
  • 正文 我和宋清朗相戀三年,在試婚紗的時候發(fā)現(xiàn)自己被綠了腊嗡。 大學(xué)時的朋友給我發(fā)了我未婚夫和他白月光在一起吃飯的照片着倾。...
    茶點(diǎn)故事閱讀 40,110評論 1 351
  • 序言:一個原本活蹦亂跳的男人離奇死亡,死狀恐怖燕少,靈堂內(nèi)的尸體忽然破棺而出卡者,到底是詐尸還是另有隱情,我是刑警寧澤客们,帶...
    沈念sama閱讀 35,792評論 5 346
  • 正文 年R本政府宣布崇决,位于F島的核電站,受9級特大地震影響底挫,放射性物質(zhì)發(fā)生泄漏恒傻。R本人自食惡果不足惜,卻給世界環(huán)境...
    茶點(diǎn)故事閱讀 41,455評論 3 331
  • 文/蒙蒙 一建邓、第九天 我趴在偏房一處隱蔽的房頂上張望盈厘。 院中可真熱鬧,春花似錦官边、人聲如沸沸手。這莊子的主人今日做“春日...
    開封第一講書人閱讀 32,003評論 0 22
  • 文/蒼蘭香墨 我抬頭看了看天上的太陽契吉。三九已至跳仿,卻和暖如春,著一層夾襖步出監(jiān)牢的瞬間栅隐,已是汗流浹背塔嬉。 一陣腳步聲響...
    開封第一講書人閱讀 33,130評論 1 272
  • 我被黑心中介騙來泰國打工, 沒想到剛下飛機(jī)就差點(diǎn)兒被人妖公主榨干…… 1. 我叫王不留租悄,地道東北人谨究。 一個月前我還...
    沈念sama閱讀 48,348評論 3 373
  • 正文 我出身青樓,卻偏偏與公主長得像泣棋,于是被迫代替她去往敵國和親胶哲。 傳聞我的和親對象是個殘疾皇子,可洞房花燭夜當(dāng)晚...
    茶點(diǎn)故事閱讀 45,047評論 2 355