mysql5.6版本的優化

1. 目標

l 瞭解什麼是優化mysql

l 掌握優化查詢的方法sql

l 掌握優化數據庫結構的方法數據庫

l 掌握優化MySQL服務器的方法服務器

2. 什麼是優化?

l 合理安排資源、調整系統參數使MySQL運行更快、更節省資源。多線程

l 優化是多方面的,包括查詢、更新、服務器等。數據庫設計

l 原則:減小系統瓶頸,減小資源佔用,增長系統的反應速度。函數

3. 數據庫性能參數

l 使用SHOW STATUS語句查看MySQL數據庫的性能參數性能

  • SHOW STATUS LIKE 'value‘

l 經常使用的參數:優化

  • Slow_queries  慢查詢次數
  • Com_(CRUD) 操做的次數
  • Uptime  上線時間

 

SHOW STATUS LIKE ‘Slow_queries‘spa

SHOW STATUS LIKE ‘Com_insert‘

SHOW STATUS LIKE ‘Com_delete‘

SHOW STATUS LIKE ‘Com_update‘

 

4. 查詢優化

4.1. EXPLAIN

MySQL中可使用EXPLAIN查看SQL執行計劃,用法:EXPLAIN SELECT * FROM tb_item

 

 

 

4.2. 結果說明

4.2.1. id

SELECT識別符。這是SELECT查詢序列號。這個不重要。

4.2.2. select_type

表示SELECT語句的類型

 

有如下幾種值

一、 SIMPLE
表示簡單查詢其中不包含鏈接查詢和子查詢

二、 PRIMARY
表示主查詢或者是最外面的查詢語句

 

 

三、 UNION
表示鏈接查詢的第2個或後面的查詢語句。

 

 

四、 DEPENDENT UNION
UNION中的第二個或後面的SELECT語句,取決於外面的查詢。

五、 UNION RESULT
鏈接查詢的結果

六、 SUBQUERY
子查詢中的第1SELECT語句。

 

 

七、 DEPENDENT SUBQUERY
子查詢中的第1SELECT語句,取決於外面的查詢。

八、 DERIVED
SELECT(FROM 子句的子查詢)

4.2.3. table

表示查詢的表

4.2.4. type重要的是否須要優化的排除手段

表示表的鏈接類型

如下的鏈接類型的順序是從最佳類型到最差類型

 

一、 system
表僅有一行,這是const類型的特列,平時不會出現,這個也能夠忽略不計。

二、 const
數據表最多隻有一個匹配行,由於只匹配一行數據,因此很快,經常使用於PRIMARY KEY或者UNIQUE索引的查詢,可理解爲const是最優化的

 

 

三、 eq_ref
mysql手冊是這樣說的:"對於每一個來自於前面的表的行組合,從該表中讀取一行。這多是最好的聯接類型,除了const類型。它用在一個索引的全部部分被聯接使用而且索引是UNIQUEPRIMARY KEY"eq_ref能夠用於使用=比較帶索引的列。

 

 

四、 ref
查詢條件索引既不是UNIQUE也不是PRIMARY KEY的狀況ref可用於=<>操做符的帶索引的列。

 

 

五、 ref_or_null
該聯接類型如同ref,可是添加了MySQL能夠專門搜索包含NULL值的行。在解決子查詢中常用該聯接類型的優化。

 

上面這五種狀況都是很理想的索引使用狀況。

下面的必需要優化

六、 index_merge
該聯接類型表示使用了索引合併優化方法。在這種狀況下,key列包含了使用的索引的清單,key_len包含了使用的索引的最長的關鍵元素。

七、 unique_subquery
該類型替換了下面形式的IN子查詢的ref: value IN (SELECT primary_key FROM single_table WHERE some_expr)
unique_subquery是一個索引查找函數,能夠徹底替換子查詢,效率更高。

八、 index_subquery
該聯接類型相似於unique_subquery。能夠替換IN子查詢,但只適合下列形式的子查詢中的非惟一索引: value IN (SELECT key_column FROM single_table WHERE some_expr)

九、 range
只檢索給定範圍的行,使用一個索引來選擇行。

 

 

十、 index
該聯接類型與ALL相同,除了只有索引樹被掃描。這一般比ALL,由於索引文件一般比數據文件小。

十一、 ALL
對於每一個來自於先前的表的行組合,進行完整的表掃描。(性能最差)

4.2.5. possible_keys

指出MySQL能使用哪一個索引在該表中找到行。

若是該列爲NULL,說明沒有使用索引能夠對該列建立索引來提升性能

4.2.6. key

顯示MySQL實際決定使用的鍵(索引)。若是沒有選擇索引,鍵是NULL

能夠強制使用索引或者忽略索引

 

 

 

4.2.7. key_len

顯示MySQL決定使用的鍵長度。若是鍵是NULL,則長度爲NULL

 

注意:key_len是肯定了MySQL將實際使用的索引長度

 

4.2.8. ref

顯示使用哪一個列或常數與key一塊兒從表中選擇行。

4.2.9. rows

顯示MySQL認爲它執行查詢時必須檢查的行數。

4.2.10. Extra

該列包含MySQL解決查詢的詳細信息

  • Distinct:MySQL發現第1個匹配行後,中止爲當前的行組合搜索更多的行。
  • Not exists:MySQL可以對查詢進行LEFT JOIN優化,發現1個匹配LEFT JOIN標準的行後,再也不爲前面的的行組合在該表內檢查更多的行。
  • range checked for each record (index map: #):MySQL沒有發現好的可使用的索引,但發現若是來自前面的表的列值已知,可能部分索引可使用。
  • Using filesort:MySQL須要額外的一次傳遞,以找出如何按排序順序檢索行。
  • Using index:從只使用索引樹中的信息而不須要進一步搜索讀取實際的行來檢索表中的列信息。
  • Using temporary:爲了解決查詢,MySQL須要建立一個臨時表來容納結果。
  • Using where:WHERE 子句用於限制哪個行匹配下一個表或發送到客戶。
  • Using sort_union(...), Using union(...), Using intersect(...):這些函數說明如何爲index_merge聯接類型合併索引掃描。
  • Using index for group-by:相似於訪問表的Using index方式,Using index for group-by表示MySQL發現了一個索引,能夠用來查 詢GROUP BYDISTINCT查詢的全部列,而不要額外搜索硬盤訪問實際的表。

4.3. 使用索引查詢須要注意

索引能夠提供查詢的速度但並非使用了帶有索引的字段查詢都會生效有些狀況下是不生效的須要注意

4.3.1. 使用LIKE關鍵字的查詢

在使用LIKE關鍵字進行查詢的查詢語句中若是匹配字符串的第一個字符爲%」,索引不起做用只有%」不在第一個位置,索引纔會生效

 

 

4.3.2. 使用聯合索引的查詢

MySQL能夠爲多個字段建立索引一個索引能夠包括16個字段。對於聯合索引,只有查詢條件中使用了這些字段中第一個字段時,索引纔會生效。

以下表tb_cart中建表是聲明2個索引(聯合) 順序是user_id和item_id   

 

 

 

 

4.3.3. 使用OR關鍵字的查詢

查詢語句的查詢條件中只有OR關鍵字OR先後的兩個條件中的列都是索引時索引纔會生效不然索引不生效

 

 

 

 

4.4. 子查詢優化

MySQL4.1版本開始支持子查詢,使用子查詢進行SELECT語句嵌套查詢,能夠一次完成不少邏輯上須要多個步驟才能完成的SQL操做。

 

子查詢雖然很靈活可是執行效率並不高

 

執行子查詢時,MYSQL須要建立臨時表查詢完畢後再刪除這些臨時表因此子查詢的速度會受到必定的影響

 

優化:

可使用鏈接查詢JOIN代替子查詢鏈接查詢時不須要創建臨時表其速度比子查詢快

5. 數據庫結構優化

一個好的數據庫設計方案對於數據庫的性能每每會起到事半功倍的效果

 

須要考慮數據冗餘、查詢和更新的速度、字段的數據類型是否合理等多方面的內容。

5.1. 將字段不少的表分解成多個表

對於字段較多的表若是有些字段的使用頻率很低能夠將這些字段分離出來造成新表

 

由於當一個表的數據量很大時會因爲使用頻率低的字段的存在而變慢

 

5.2. 增長中間表

對於須要常常聯合查詢的表能夠創建中間表以提升查詢效率

 

經過創建中間表將須要經過聯合查詢的數據插入到中間表中而後將原來的聯合查詢改成對中間表的查詢

5.3. 增長冗餘字段

設計數據表時應儘可能遵循範式理論的規約儘量的減小冗餘字段讓數據庫設計看起來精緻、優雅。可是,合理的加入冗餘字段能夠提升查詢速度。

 

表的規範化程度越高表和表之間的關係越多須要鏈接查詢的狀況也就越多性能也就越差

 

注意:

冗餘字段的值在一個表中修改了就要想辦法在其餘表中更新不然就會致使數據不一致的問題。

6. 插入數據的優化

插入數據時影響插入速度的主要是索引惟一性校驗一次插入的數據條數等

 

插入數據的優化不一樣的存儲引擎優化手段不同,在MySQL經常使用的存儲引擎有,MyISAMInnoDB二者的區別

 

 

 

6.1. MyISAM

6.1.1. 禁用索引

對於非空表插入記錄時,MySQL會根據表的索引對插入的記錄創建索引若是插入大量數據創建索引會下降插入數據速度

 

爲了解決這個問題能夠在批量插入數據以前禁用索引數據插入完成後再開啓索引

 

禁用索引的語句

ALTER TABLE table_name DISABLE KEYS

 

開啓索引語句

ALTER TABLE table_name ENABLE KEYS

 

對於空表批量插入數據則不須要進行操做由於MyISAM引擎的表是在導入數據後才創建索引

6.1.2. 禁用惟一性檢查

惟一性校驗會下降插入記錄的速度能夠在插入記錄以前禁用惟一性檢查插入數據完成後再開啓

 

禁用惟一性檢查的語句SET UNIQUE_CHECKS = 0;

 

開啓惟一性檢查的語句:SET UNIQUE_CHECKS = 1;

6.1.3. 批量插入數據

插入數據時可使用一條INSERT語句插入一條數據也能夠插入多條數據

 

第二種方式的插入速度比第一種方式快

6.1.4. 使用LOAD DATA INFILE

當須要批量導入數據時,使用LOAD DATA INFILE語句INSERT語句插入速度快不少。

6.2. InnoDB

6.2.1. 禁用惟一性檢查

用法和MyISAM同樣

6.2.2. 禁用外鍵檢查

插入數據以前執行禁止對外鍵的檢查數據插入完成後再恢復,能夠提供插入速度。

 

禁用:SET foreign_key_checks = 0;

開啓:SET foreign_key_checks = 1;

6.2.3. 禁止自動提交

插入數據以前執行禁止事務的自動提交數據插入完成後再恢復,能夠提升插入速度。

 

禁用:SET autocommit = 0;

開啓:SET autocommit = 1;

7. 服務器優化

7.1. 優化服務器硬件

服務器的硬件性能直接決定着MySQL數據庫的性能硬件的性能瓶頸直接決定MySQL數據庫的運行速度和效率

 

須要從如下幾個方面考慮

一、 配置較大的內存。足夠大的內存,是提升MySQL數據庫性能的方法之一。內存的IO比硬盤快的多,能夠增長系統的緩衝區容量,使數據在內存停留的時間更長,以減小磁盤的IO

二、 配置高速磁盤,好比SSD

三、 合理分配磁盤IO,把磁盤IO分散到多個設備上以減小資源的競爭提升並行操做能力

四、 配置多核處理器,MySQL是多線程的數據庫多處理器能夠提升同時執行多個線程的能力

7.2. 優化MySQL的參數

經過優化MySQL的參數能夠提升資源利用率從而達到提升MySQL服務器性能的目的

 

MySQL的配置參數都在my.conf或者my.ini文件的[mysqld]組中,經常使用的參數以下:

 

 

 

 

相關文章
相關標籤/搜索