Expert 診斷優化系列------------------內存不夠用么?


    現在很多用戶被數據庫的慢的問題所困擾,又苦於花錢請一個專業的DBA成本太高。軟件維護人員對數據庫的了解又不是那么深入,所以導致問題遲遲不能解決,或只能暫時解決不能得到根治。開發人員解決數據問題基本又是搜遍百度各種方法嘗試個遍,可能錯過診斷問題的最佳時機又可能嘗試一堆方法最后無奈放棄。

    怎么樣讓瑣事纏身的程序維護人員,用最快的方式解決數據庫出現的問題?怎么讓我們程序員的痛苦降低到最小...每天喝喝茶水,看看新聞平安度過一天呢?本系列重要通過Expert for sqlserver 工具講解下數據庫遇到的各種問題的表象及導致這樣問題的根本原因,讓定位問題更准確,解決問題思路更清晰!!

    數據庫的性能好壞,對於最終用戶來說表現為點擊的操作是否能夠快速響應,那么反應到數據庫上就是語句執行時間是否夠短!

    對用運維人員數據庫性能的表現,簡單可能看成CPU 、內存、磁盤三巨頭指標是否正常,上一篇講述了CPU的基本診斷

Expert 診斷優化系列------------------你的CPU高么?

    本篇我們就從內存下手,看看內存能夠看出哪些問題!

廢話不多說,直接開整-----------------------------------------------------------------------------------------

    首先說明一個誤區,你是否被這樣的畫面所震驚?

    

 

    我的服務器內存滿了,就是這個導致我數據庫慢!我的程序報錯也是因為這個,什么都因為內存滿了!!  趕緊加內存吧~ 

    這個答案是大寫的 “不一定,SQL SERVER是一個很愛內存的家伙,他會緩存你的數據,執行計划,連接信息等等,所以出現這個現象是很正常的,不要輕易下結論,除非你經過仔細的研究和分析!

    那么怎么去分析到底是不是內存不足導致的問題呢?  下面我們來說說!

主要用到的性能計數器(不知道什么是性能計數器的,請自行百度)

  1. Page life expectancy (數據庫計數器:主要顯示不被使用的頁,將在緩存中停留的秒數 )
  2. Lazy writes/sec  (數據庫計數器:惰性寫入器會在內存有壓力且有新的內存需求時觸發,成批的刷新“老化的緩沖區”)
  3. Page Reads/sec,Page Writes/sec  (這里使用數據庫級別計數器:當需要讀取或寫入的頁不在內存中,需要到磁盤中讀取時計數)
  4. Target Server Memory (KB)  (SQL server能夠使用的內存總量)
  5. Total Server Memory (KB)  (SQL SERVER使用的內存總量,這里指BUFFER POOL的大小)
  6. Available MBytes  (系統系數器:主要顯示系統還有多少可用內存)

  注:Target Server Memory (KB) - Total Server Memory (KB) 約等於SQL SERVER還可以使用的內存數

 

  Available MBytes 主要顯示系統中還多少空閑內存 (如果這個值較大,而SQL SERVER還可以使用的內存數為0或者較小,可以適當的調大max server memory(最大內存,稍后介紹))

    

   這里不再細說這三個計數器,我們主要通過前三個計數的聯動來判斷系統的內存是否真的存在壓力!!!

   首先介紹一下,這三個計數器是如何聯動的?

   概念出發:Page life expectancy 不被使用的頁在緩存中停留的秒數,如果低說明內存壓力

        Page Reads/sec 所要讀的數據不在內存中需要物理讀取

        Lazy writes/sec 內存壓力時成批的刷新老化緩沖區 

   當一個操作需要大量讀取數據,且數據頁不在緩存中 ——》 那么需要大量從磁盤讀取冷數據放入緩存(Page Reads/sec 升高) ——》緩存有明顯壓力的時候Lazy writes/sec就會觸發(Lazy writes/sec升高),大批量的將老化的數據或緩存計划等刷出緩存 ——》數據被清出緩存,那么頁生命周期就會下降(Page life expectancy)

    

    Page Reads/sec

    

    Lazy writes/sec

    

    Page life expectancy

    

 

 

    高能預警:當你看到自己的計數器是這個樣子的時候,你給的出結論不應該單單是,我內存有壓力!

    這個例子不光為了說明三計數器是聯動,而且也可以看出規律,那就是每三小時一次明顯的內存壓力。正如第一篇CPU文章的介紹,這種規律性的表象,作為系統的維護人員,一定要仔細想想什么操作導致的問題?不要因為一個簡單的配置問題而拖慢了整個系統!

    我通過對問題時間點的語句分析發現,這個系統每三小時進行一次日志備份,正常的日志備份不會導致這樣的現象,但如果在日志備份的時候加上CHECKDB呢?

    這就是所說的不要因為一個小的失誤而影響整個系統!

 

--------------------------------------------------------------------------------------------

系統內存不足的表象          

    下面展示一個內存壓力的服務器這三個計數器的表象:

    Page Reads/sec

    

    Lazy writes/sec    

    

    Page life expectancy 頁生命周期

    

 

     

    這幾個計數器反應出的問題絕對是系統內存嚴重不足,計數器雙高一低。那么當我們知道系統內存不足的時候應該怎么辦呢?加內存么?

    不要急,下面我們說說如何讓你的系統節省內存,也許做過這一輪優化,你的系統內存就夠用了! 你沒聽錯,就是-----優化!

 

優化-----讓你的內存無壓力

 

    你要給你的系統設置最大內存max server memory   

    

 

 

    問:我系統內存本來就不夠為什么還要設置使用上限?我這服務器就給數據庫用還用設置?

   答:數據庫是運行在windows 上的應用,他和notepad對於操作系統來說本質上沒區別,那么這就好比君(操作系統)與 臣(數據庫)的關系。

    而SQL SERVER是一個很喜歡內存的應用,所以很可能吃掉大量內存導致windows系統沒有足夠內存使用,,那么這時候君臣關系就體現的淋漓盡致了,君(windows) 要臣(SQL SERVER)死(釋放內存)臣不得不死呀...這個釋放在一定程度上可不是單單讓windows夠用了,很可能導致SQL內存陡降,以致SQL 短時間假死(操作無響應)。所以為了你數據庫的穩定性,這個最大上限一定要設置。

 

    內存設置推薦:

    一般我比較推薦如果內存較小操作系統預留3G-4G ,如果內存大256或512以上在數據庫內存無壓力時預留5%給操作系統,剩下給SQL SERVER ,如果服務器還有其他應用還要在SQL 中減掉應用所占的內存。

    如果內存比較小且數據庫內存壓力大,則可以通過前面講述的Available MBytes 的判斷結果適量給系統預留內存。

 

    

    注意:最大內存的設置單位為 MB

 

語句的優化,讓語句消耗內存更少!

    語句優化系列請關注后續文章,這里只針對降低內存

    降低內存對語句優化主要集中在幾個方面:

  1. 是否缺失索引? 
  2. 消耗內存的操作是否可以消除(如排序)
  3. 降低語句復雜性,讓優化器能選用最佳計划

 

    語句消耗內存主要體現在大量的讀取,或者有排序等操作。限於篇幅這里只做簡單的例子,詳細的語句優化請關注后續文章。

    所謂的讀,寫簡單理解就是在語句執行時所需要用到的數據頁數,需要的越多就需要越大的內存來緩存這些數據頁。如果需要的頁不在內存中還需要從磁盤讀取 (磁盤讀取就是為什么Page Reads/sec 會高

    

 

    簡單的一個加索引降低邏輯讀的例子~

    

 

    

    

    語句使用了一個整個表掃描的計划,執行了 19秒,邏輯讀取143800次,預讀137236 (磁盤上讀取),消耗了40KB 的內存 ,並且明確提示出缺少索引!

    那么我們加上提示缺少的索引,再次執行

    

    

 

    加上索引的語句執行不到1秒 邏輯讀降低到13次,內存消耗已經可以忽略不計。這就是索引對語句的重要性!單條語句如此,你的系統中到底有多少這樣的語句呢?

    

 

 

    再來看一個寫法修改的例子 :

    

    

    

 

 

    只是簡單的改了下語句的寫法時間有7秒變成1秒,內存消耗從300+MB 變成 1MB

    

    這兩個例子,告訴我們也許系統中簡簡單單做一些調整,內存的壓力就會明顯降低或者變得非常充足,所以在你下了一個需要購買內存的決定前,是否針對系統的語句進行過調優?

      

-----------------------------------------------------------------------------------------------------

 

 對於內存性能計數器的閥值簡單說明

 

 Page life expectancy 計數器這個時間要高於多少才算正常呢?

    答:很多資料上多這個值都有誤解,說是300S,300S是在十多年前的一個參考值,是基於當時的服務器內存受到4GB內存的限制的影響得到的,

  目前服務器內存動輒超過100GB的情況下,用同樣的標准,顯然是不夠准確的,這個值的計算是跟具體的服務器內存配置有關的,一個可供參考的標准算法是 Max Buffer Pool(GB)/4*300(S)

 

 

 

為什么這里缺少了一個 Buffer Cache hit ratio 計數器?

很多材料上都介紹其閾值是90%,95%之類的參考值,其實都是錯誤的,

    其實真正觀察過的人,早就會發現,從PLE和Buffer hit ratio得出根本不一致的結論。

 

詳細說明請參見:wy123的博客

Sql Server 內存相關計數器以及內存壓力診斷

Buffer cache hit ratio性能計數器真的可以作為內存瓶頸的判斷指標嗎?

 

 

 

 -----------------------------------------------------------------------------------------------------

  總結:內存對於數據庫來說是最為重要的依賴之一,內存的問題診斷和優化對系統至關重要。

     優化語句可以讓你的系統內存壓力明顯降低。

     語句優化所帶來的效果,在很大程度上會比添加硬件更有效!

     作為一個技術人員對於系統問題的定位、分析、調優是最重要的,如果內存問題都通過加內存來解決,我們的價值何在呢?

 

 

 

 ----------------------------------------------------------------------------------------------------

注:此文章為原創,歡迎轉載,請在文章頁面明顯位置給出此文鏈接!
若您覺得這篇文章還不錯請點擊下右下角的推薦,非常感謝!

  引用高大俠的一句話 :“拒絕SQL Server背鍋,從我做起!”

為了方便閱讀給出系列文章的導讀鏈接:

SQL SERVER全面優化-------Expert for SQL Server 診斷系列


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM