大數據量表的優化查詢


一、對於運算邏輯,盡可能將要統計的各項目整合在一個查詢語句中計算,而不是用分組條件或分項目調用多個查詢語句,而后在代碼里計算結果。

二、查詢語句的優化,諸如不用"select *"、多表關聯查詢時添加別名於查詢字段上、避免使用in、not in關鍵字、非去除重復時用union all替換union、先過濾后分組、排序等等。

三、在無法更改數據結構、不影響其它業務操作情況下,為查詢、統計項建立索引,這里有一段關於創建索引的話:

創建索引的原則總結如下:(來自:http://club.topsage.com/thread-1584965-1-1.html)
    首先要判斷表的存儲數據量大小、高性能的操作要求(是頻繁增刪改操作還是頻繁的查詢操作)。對於要求頻繁增刪改操作的表,建立索引可能只會起到反作用。
  1. 對於只有幾十、幾百條記錄的表,建立索引的效果可能還不如逐行掃描來得快
  2. 對於只有幾個可能值的字段,最常見的如性別等字段,建立索引是無意義的
  3. 對於在查詢語句的WHERE子句中頻繁出現的字段可以建立索引,但注意如果索引字段上存在函數,該索引失效。如:WHERE SUBSTR(NAME,1)=’N’;NAME字段上的索引不會起作用,改寫成WHERE NAME LIKE ‘N%’, NAME字段上的索引才能生效。另外IS NULL和IS NOT NULL也會使索引失效
  4. 適量的冗余字段可以減小查詢的開銷,雖然這樣做不符合數據庫范式的要求
  5. 建立在大數據類型字段上的索引沒有意義,比如SQLSERVER的IMAGE,ORACLE的LOB

四、盡可能增大分配給數據庫服務器的內存,sql語句的運算都是在內存中完成的,如果分配的內存過小,對於大量數據的運算雖不會導致內存溢出,但是運算速度會非常的慢。

 

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

    1:索引,我們最先想到的就是創建索引,創建索引可以成倍的提升查詢的效率,節省時間。但是如果數據量太過於巨大的時候,這個時候單純的創建索引是無濟於事的,我們知道假如特別是在大數據量中統計查詢,就拿1000W數據來說吧,如果使用count函數的話,最少要50-100秒以上,當然如果你的服務器配置夠高,處理夠快,或許會少很多但是一樣會超過10秒。

  單純的建立索引是無濟於事的。我們可以在創建索引的時候給索引加個屬性,compress,這個屬性可以將所創建的索引進行一個良好的歸類,這樣的話,查詢速度會提升5-10倍,或者更高。但是唯一的缺點是,壓縮索引只能手動創建,對於那些KEY是無法進行壓縮的,因為KEY(主鍵)是自動創建的索引,compress必選的屬性,一般默認是不創建。所以在創建壓縮索引的時候,可以找其他的關鍵字段進行壓縮,比如工單表里面的流水號

  2:盡量少的使用那些函數,比如 IS NUll;IS NOT NULL,IN;NOT IN等這樣的匹配函數,可以使用符號程序進行操作

  3:盡量少使用子查詢,如果你寫個類,里面模仿子查詢的效果,你就會發現,簡直在要命,我們可以使用聯合查詢,或者是外連接查詢,這樣速度會比子查詢快很多。

  4:在使用索引的時候,注意如下:

  Where子句中有"!="將使索引失效

  select account_name from test where amount != 0  (不使用)

  select account_name from test where amount > 0  (使用)

  Where條件中對字段增加處理函數將不使用該列的索引

  select * from emp where to_char(hire_date,'yyyymmdd')='20080411' (不使用)

  select * from emp where hire_date = to_char('20080411','yyyymmdd') (使用)

  避免在索引列上使用IS NULL和 IS NOT NULL

  select * from emp where dept_code is not null  (不使用)

  select * from emp where dept_code > 0  (使用)

  通配符% 的使用

  select * from emp where name like '%A'  (不使用索引)

  select * from emp where name like 'A%'  (使用索引)

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

    http://www.2cto.com/database/201411/348519.html

 

(1).優化索引

通過添加索引后,查詢的效率得到極大的提升,常用查詢的查詢時間從原來的幾十秒下降到幾秒。

建立以下兩個單列索引

ALTERTABLE population , ADD INDEX fk_city(city)  ,ADD INDEX fk_birthday(birthday);

也可以建立以下兩個組合索引

 

建立組合索引

ALTERTABLE  population  ADD INDEX fk_index1(city,birthday),ADD INDEX fk_index2(birthday,city);

 

(2).使用中間表
     雖然索引優化可以將查詢時間大大減少,但如果數據量達到一定量時,有些情況下索引到的數據達到幾百萬時,查詢仍然會很慢,因此索引優化 無法從根本上解決問題。現在表中的數據量越來越大,平均每個月要增加一兩百萬的數據,索引的優化方法只是暫時的,只能解決小數據量的查詢問題,隨着數據量的快速增長,索引帶來的性能優化很容易達到極限,要尋找其他的解決方案。

 我們根據業務需求的特點,創建中間表population_statistics,將表population中的統計數據存放到中間表population_statistics中,查詢時 直接從中間表population_statistics中查詢。注意,在對表population進行增、刪、改時,必須同時更新population_statistics中的數據,否則會出現數據不一致的錯誤!

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

主表A 20多W條數據,內連接了視圖B兩次,視圖B有20多W條數據,然后又左連接了一個40多W條數據的表,總的查詢再group by了一下,被by的字段有十幾個,select中有一些字段做了一些sum計算,還select了一些其它字段,where有一些動態生成的查詢條件,對應一個搜索頁面,搜索條件根據用戶選擇生成,我做索引前查詢需要5分鍾,做了之后也要100多秒,原來所有的查詢是寫在一個存儲過程來調用的,動態生成的查詢條件也寫在過程里,調用一個大視圖來查詢我前面講的這些,我把查詢條件直接寫到視圖里的話,可以縮短到50多秒,看來還是寫進去比較好啊,但再也沒辦法再縮短了,要命的是,查詢條件還有一些是數值比較的,是通過一些字段的計算再與其比較的,如果在where后面寫一些字段的運算再比較,無疑效率很低,也用不上索引,有沒有比較好的辦法再優化一下。


免責聲明!

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



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