数据库优化的方法及步骤
? ? ? ?先簡(jiǎn)單介紹下博主 面臨的情況,17年底,一個(gè)用了5年的售后系統(tǒng)處于要升級(jí)換代又因?yàn)槠渌驅(qū)е聲簳r(shí)不能升級(jí)的情況,所以需要在不動(dòng)大的架構(gòu)的情況來做優(yōu)化。具體有個(gè)呼叫中心,坐席會(huì)一直在接電話,60人左右,電話保存時(shí)有個(gè)很復(fù)雜的派單邏輯,要優(yōu)先保證效率。外面管理員,維修工,操作員3000+。
? ? ? ?先用代碼整理下,看看各個(gè)表都是多大
--Script1: --查看某數(shù)據(jù)庫(kù)所有表的信息 DECLARE @tablespaceinfo TABLE ([name] SYSNAME,[rows] BIGINT,[reserved] VARCHAR(100),[data] VARCHAR(100),[index_size] VARCHAR(100),[unused] VARCHAR(100) )DECLARE @tablename VARCHAR(255);DECLARE Info_cursor CURSOR FORSELECT '['+[name]+']' FROM sys.tables WHERE TYPE='U';OPEN Info_cursor FETCH NEXT FROM Info_cursor INTO @tablenameWHILE @@FETCH_STATUS = 0 BEGININSERT INTO @tablespaceinfo EXEC sp_spaceused @tablenameFETCH NEXT FROM Info_cursor INTO @tablename ENDCLOSE Info_cursor DEALLOCATE Info_cursorSELECT * FROM @tablespaceinfoORDER BY Cast(Replace(reserved,'KB','') AS INT) DESC復(fù)制下來直接執(zhí)行就好,結(jié)果是數(shù)據(jù)庫(kù)大致400G,最大的表為客戶檔案和客戶資產(chǎn),分別有2000萬條和1800萬條數(shù)據(jù)這兩個(gè)數(shù)據(jù)表,之前優(yōu)化后已經(jīng)對(duì)表做了分區(qū),具體可以看表分區(qū),下面是要先對(duì)呼叫中心反映的卡頓做對(duì)應(yīng)的處理,說是電話接入后要10-20秒才會(huì)有反應(yīng),需要出畫面打開慢的原因。
開始以為是兩個(gè)大表的原因,后面發(fā)現(xiàn)不是,下面介紹下最快速發(fā)現(xiàn)問題的工具。
框框中標(biāo)識(shí)的是活動(dòng)監(jiān)視器,里面會(huì)有幾個(gè)非常有用的東西,我們繼續(xù)暫開說
活動(dòng)監(jiān)視器會(huì)自動(dòng)給出這些監(jiān)視的內(nèi)容,這里有兩點(diǎn)非常需要關(guān)注,最近耗費(fèi)大量資源的查詢,以及進(jìn)程。雙擊這些查詢最近耗費(fèi)大量資源的查詢,會(huì)看到具體的語(yǔ)句。我們這時(shí)只要在其中發(fā)現(xiàn)我們需要優(yōu)化的界面中存在的語(yǔ)句調(diào)用的內(nèi)容,就可以做對(duì)應(yīng)處理。同時(shí)插一句,如果讓這里耗費(fèi)大量資源語(yǔ)句的都得到優(yōu)化就已經(jīng)極大的完成了任務(wù)了。
這個(gè)是我找出來的問題的存儲(chǔ)過程,發(fā)現(xiàn)這個(gè)執(zhí)行起來非常慢大概需要15秒,雖然看著表很多,但總覺得不至于。圖中可以發(fā)現(xiàn),有大量的DATEADD(MM,-6,GETDATE())為了獲取最近6個(gè)月的服務(wù)數(shù)據(jù),那就簡(jiǎn)單了,創(chuàng)建個(gè)變量代替這個(gè)就行。現(xiàn)在這個(gè)存儲(chǔ)過程被壓縮到2秒,另外說一句,就算不用運(yùn)算getdate這個(gè)函數(shù),取一次,然后用變量代替getdate也會(huì)比現(xiàn)在優(yōu)化很多,不需要反復(fù)去數(shù)據(jù)庫(kù)取時(shí)間。
下面是進(jìn)程
這是當(dāng)時(shí)上線一個(gè)外部app端后的情況,可以發(fā)現(xiàn)目前的資源等待已經(jīng)很嚴(yán)重了,高達(dá)8517毫秒,雖然阻塞者都是自己273,但其實(shí)是有很多可以優(yōu)化的空間的。雙擊,可以看到詳細(xì)的回話信息,里面的內(nèi)容可以拷出來單獨(dú)優(yōu)化。語(yǔ)句中有個(gè)*非常的扎眼,這里說下當(dāng)你想在select子句中列出所有的列時(shí),使用動(dòng)態(tài)sql列引用“*”是一個(gè)方便的方法,不幸的是,是一種非常低效的方法。sql解析過程中,還需要把“*”依次轉(zhuǎn)換為所有的列名,這個(gè)工作需要查詢數(shù)據(jù)字典完成!后續(xù)查看該視圖,又將里面的UNION ALL拆分,將該語(yǔ)句效率提升了3倍左右。
在最下方還有個(gè)SELECT? COUNT (*) from的語(yǔ)句,可能這是學(xué)校里教法,但實(shí)際應(yīng)用中把count(*)換成count(1)在改語(yǔ)句中竟然可以提升60%的效率,親測(cè)有效。
最后帶一下概述
這里的計(jì)數(shù)器是反應(yīng)服務(wù)器性能的,如果其他方面沒用,只能通過提升硬件了。挑選服務(wù)器已經(jīng)在前面提過。
在這問題優(yōu)化過后,數(shù)據(jù)庫(kù)還經(jīng)歷了很多事務(wù)方面的優(yōu)化,打算在后面單獨(dú)講,包括臟讀幻讀需要的注意點(diǎn),性能和準(zhǔn)確性的兼顧,這些都是需要統(tǒng)籌考慮的。活動(dòng)監(jiān)視器這個(gè)sql的神器,希望可以得到更改的應(yīng)用,幫到大家,一般小問題都可以比較簡(jiǎn)單的從這里面發(fā)現(xiàn)
經(jīng)過1個(gè)月的優(yōu)化,這套服務(wù)了5年的系統(tǒng)終于繼續(xù)愉快的跑了起來。對(duì)于一個(gè)服務(wù)了這么多年系統(tǒng),真不容易哦。
總結(jié)
以上是生活随笔為你收集整理的数据库优化的方法及步骤的全部?jī)?nèi)容,希望文章能夠幫你解決所遇到的問題。
- 上一篇: go语言学习笔记 — 基础 — 高级数据
- 下一篇: Dubbo接口和Http接口的区别