磁盤排序對Oracle數(shù)據(jù)庫性能的影響
當建立同Oracle會話時,會在服務器內存中劃分出一個專門用來排序的區(qū)域,從而為會話提供排序空間。但是,這個排序空間畢竟有限,若記錄數(shù)量超過這個排序空間的話,就需要進行磁盤排序。但是,我們都知道,磁盤排序的執(zhí)行速度要比內存排序的執(zhí)行速度慢1400倍。而且,磁盤排序會消耗臨時表空間的資源,并且可能影響到正在進行的其他SQL排序,因為Oracle必須為臨時表空間中的數(shù)據(jù)塊分配緩沖池。而且,過多的磁盤排序會導致空閑緩沖等待,以及將執(zhí)行其他任務的數(shù)據(jù)塊從緩沖池中分頁出去。對于數(shù)據(jù)庫管理員來說,在內存中進行排序總是比磁盤排序更受歡迎。所以說,磁盤排序是影響Oracle數(shù)據(jù)庫性能的罪魁禍首。在數(shù)據(jù)庫優(yōu)化的時候,我們應該想法設法降低數(shù)據(jù)庫的磁盤排序。為此,筆者有如下建議。
一、合理設置Sort_area_size參數(shù)
雖然說Oracle10G以后的數(shù)據(jù)庫會自動對內存進行管理。但是,在一些性能要求比較高或者排序頻率比較高的數(shù)據(jù)庫中,仍然有必要對一些影響內存分配的參數(shù)進行調整。其中,最重要的一個參數(shù)就是Sort_area_size。
Oracle數(shù)據(jù)庫會為所有的鏈接Oracle會話分配Sort_area_size這個參數(shù)。所以,對于擁有大量用戶的數(shù)據(jù)庫來說,如果增加這個參數(shù)的值,會讓磁盤排序的幾率明顯降低,不過數(shù)據(jù)庫也要為此付出這個代價,很容易導致內存過載。但是,如果這個參數(shù)的值設置的過低的話,又會導致過多的磁盤排序。所以,這個參數(shù)并不是越大越好。因為這個參數(shù)如果設置的過大的話,其帶來的性能收益反而會降低。因為為了提高有限幾個查詢的速度,可能會浪費大量的內存。這無疑是我們數(shù)據(jù)庫管理員不希望看到的。
在實際工作中,我們往往需要在兩者之間進行一個均衡。設置一個合理的參數(shù),盡量讓數(shù)據(jù)庫減少磁盤排序的幾率,同時也不能使得服務器內存過載。為此筆者有一個建議。數(shù)據(jù)庫管理員應該每隔一段時間增加這個參數(shù)的值,并使用Statspack工具定時監(jiān)控內存排序與磁盤排序的數(shù)據(jù)。在起初進行調整的時候***每個小時查詢一次。通過這些數(shù)據(jù),我們就可以得到一個合理的參數(shù)值,在兩這之間取得一個均衡。
前期調整完成后,在后期仍然需要進行監(jiān)控。因為后期隨著企業(yè)應用的改變,這個參數(shù)仍然需要根據(jù)實際情況進行調整,以提高數(shù)據(jù)庫的性能
二、盡量減少不必要的磁盤排序
在某些情況下,盡管數(shù)據(jù)庫管理員沒有直接通過Order By等語句對數(shù)據(jù)庫記錄進行排序,可是Oracle數(shù)據(jù)庫服務器仍然會對查詢結果進行排序。因為這些語句需要起作用,必須要先對數(shù)據(jù)進行排序。所以,他們往往帶有隱性的排序功能。
我們在數(shù)據(jù)庫維護或者前臺應用程序設計的時候,要盡量的減少這種不必要的排序。如Distinct關鍵字,它的作用就是取消重復的記錄。但是,要實現(xiàn)這個目的的話,則數(shù)據(jù)庫必須要先對記錄進行排序,然后才能夠去除重復的記錄內容。故在設計的時候,盡量要避免使用Distinct關鍵字。其實,筆者在工作中,經常會碰到這種情況,某些記錄其實不存在重復記錄,但是程序開發(fā)人員為了保障數(shù)據(jù)的準確性,就在SQL語句中加入了Distinct關鍵字,從而造成了不必要的排序。
另外,在其他一些情況下,也會導致不必要的排序。如排序合并連接,也會導致不必要的排序。故無論何時,只要使用了排序合并連接,就會執(zhí)行排序已連接關鍵值。故在數(shù)據(jù)庫與應用程序設計的時候,要盡量避免排序合并連接。其實,在許多情況下,嵌套循環(huán)連接反而使更好的選擇。因為這個嵌套循環(huán)連接,它更加有效而且不會導致不必要的排序以及不比要的全表掃描。
其次,有時候缺失索引也會導致一些并不要的排序。故數(shù)據(jù)庫管理員在平時的工作中,要盡量的減少這些不必要的排序,以讓寶貴的內存資源交給更重要的任務來適用,提高Oracle數(shù)據(jù)庫性能。
#p#三、利用Statspack工具監(jiān)控排序活動
Statspack工具是一款提高Oracle數(shù)據(jù)庫性能的很好的輔助工具。因為它可以幫助我們收集很多有用的信息。故我們數(shù)據(jù)庫管理員也可以利Statspack工具對數(shù)據(jù)庫中的排序活動進行監(jiān)控。
對于一個有經驗的數(shù)據(jù)庫管理員來說,對內存排序和磁盤排序保持必要的排需是非常必要的。因為我們無法左右用戶的行為;而用戶的行為又會有所調整。用戶在調整的過程中,有可能又會增加額外的磁盤排序。當然,也有可能磁盤排序的幾率會減少。但是,通常情況下,隨著用戶交易數(shù)據(jù)的增加,這個磁盤排序的幾率在理論上仍然是往上爬的。而實際上也是往上升的,只是這個升的速度沒有理論上那么快而已。這主要是看數(shù)據(jù)庫管理員如何進行管理了。
根據(jù)筆者的了解,企業(yè)用戶的操作往往會有一個周期性的變化,如按年或者按月進行周期性的變化。數(shù)據(jù)庫管理員應該養(yǎng)成一個好習慣,每個月利用Statspack工具定期的對數(shù)據(jù)庫進行監(jiān)控。特別是要監(jiān)控數(shù)據(jù)庫的排序情況。Statspack工具還有額外的一個功能,就是自動監(jiān)測與警告功能。也就是說,可以讓Statspack這個工具在磁盤排序數(shù)量超過一個預設置的閥值時,自動給數(shù)據(jù)庫管理員發(fā)送一個警告,如通過郵件形式發(fā)送給管理員等等。筆者通過監(jiān)控發(fā)現(xiàn),每到月底與月初的時候,磁盤排序的數(shù)量會大大的增加。這主要是因為在月底的時候,用戶會對當月的交易數(shù)據(jù)進行統(tǒng)計。所以當月底月初的時候,由于交易記錄比較多,所以,會有比較多的磁盤排序發(fā)生。在這種情況下,數(shù)據(jù)庫管理員有必要對相關參數(shù)進行調整。不過這個調整是暫時的調整,等到這個周期過去后,仍然要把參數(shù)調回來。只有如此,數(shù)據(jù)庫的整體性能才會有所保障。即不會因為內存過載而降低數(shù)據(jù)庫性能;也不會因為磁盤排序而給數(shù)據(jù)庫造成額外的負擔。
所以,雖然排序是SQL語句執(zhí)行中 很微小的一個部分,但是其對數(shù)據(jù)庫性能影響卻比較大,而且也是非常顯著的??上У氖牵判蚴荢QL調整中往往被忽視的地方。在Oracle數(shù)據(jù)庫中,排序對用戶來說是透明的。也就是說,排序對用戶很少有所限制,用戶可以根據(jù)自己的需要來對數(shù)據(jù)進行隨意地排序。但是,用戶并不知道,什么樣的操作會降低數(shù)據(jù)庫的性能。故如何降低用戶的不合理操作而產生額外的排序,甚至是磁盤排序,這是數(shù)據(jù)庫管理員在平時工作中必須要考慮到的一個問題。通過以上三個方法,或許可以給數(shù)據(jù)庫管理員找到一些解決問題的思路。相信通過以上方法,可以***程度的減少磁盤排序的發(fā)生,不再讓磁盤排序成為影響數(shù)據(jù)庫性能的罪魁禍首。
【編輯推薦】