MySQL性能優化(一)-- 存儲引擎和三範式

1、MySQL存儲引擎

  存儲引擎說白了就是如何存儲數據、如何爲存儲的數據創建索引和如何更新、查詢數據等技術的實現方法。由於在關係數據庫中數據的存儲是以表的形式存儲的,因此存儲引擎也能夠稱爲表類型(即存儲和操做此表的類型)。MySQL5.5之後默認使用InnoDB存儲引擎。html

  下圖是MySQL中各類存儲引擎的對比。mysql

  

1.MyISAM:sql

  這種引擎是mysql最先提供的。它不支持事務,也不支持外鍵,尤爲是訪問速度快。這種引擎又能夠分爲靜態MyISAM、動態MyISAM 和壓縮MyISAM三種:數據庫

  1) 靜態MyISAM:若是數據表中的各數據列的長度都是預先固定好的,服務器將自動選擇這種表類型。由於數據表中每一條記錄所佔用的空間都是同樣的,因此這種表存取和更新的效率很是高。 當數據受損時,恢復工做也比較容易作。這種存儲方式的優勢是存儲很是迅速,容易緩存,出現故障容易恢復;缺點是佔用的空間一般比動態表多。緩存

   2) 動態MyISAM:若是數據表中出現varchar、xxxtext或xxxBLOB字段時,服務器將自動選擇這種表類型。相對於靜態MyISAM,這種表存儲空間比較小,但因爲每條記錄的長度不一,因此 屢次修改數據後,數據表中的數據就可能離散的存儲在內存中,進而致使執行效率降低。同時,內存中也可能會出現不少碎片。所以,這種類型的表要常常用optimize table命令或者myisamchk -r命令 或 優化工具來整理碎片、改善性能,而且出現故障的時候恢復相對比較困難。服務器

  3) 壓縮MyISAM:以上說到的兩種類型的表均可以用myisamchk工具壓縮。這種類型的表進一步減少了佔用的存儲,可是這種表壓縮以後不能再被修改。另外,由於是壓縮數據,因此這種表在讀取的時候要先時行解壓縮。可是,不論是何種MyISAM表,目前它都不支持事務,行級鎖和外鍵約束的功能。工具

2.Merge:性能

  這種類型是MyISAM類型的一種變種。合併表是將幾個相同的MyISAM表合併爲一個虛表。常應用於日誌和數據倉庫。優化

3.InnoDB:spa

  InnoDB表類型能夠看做是對MyISAM的進一步更新產品,它提供了事務、行級鎖機制和外鍵約束的功能。對比MyISAM的存儲引擎,InnoDB寫的處理效率差一些,而且會佔用更多 的磁盤空間以保留數據和索引。

4.memory:

  這種類型的數據表只存在於內存中。它使用HASH索引,因此數據的存取速度很是快。由於是存在於內存中,因此這種類型常應用於臨時表中,可是一旦服務器關閉,表中的數據就會丟失,但表還會繼續存在。默認狀況下,memory數據表使用散列索引,利用這種索引進行「相等比較」很是快,可是對「範圍比較」的速度就慢多了。所以,散列索引值適合使用在"="和"<=>"的操做符中,不適合使用在"<"或">"操做符中,也一樣不適合用在order by字句裏。若是確實要使用"<"或">"或betwen操做符,可使用btree索引來加快速度。

  存儲在MEMORY數據表裏的數據行使用的是長度不變的格式,所以加快處理速度,這意味着不能使用BLOB和TEXT這樣的長度可變的數據類型。VARCHAR是一種長度可變的類型,但由於它在MySQL內部看成長度固定不變的CHAR類型,因此可使用。

  使用USING HASH/BTREE來指定特定到索引:create index mem_hash using hash on tab_memory(city_id);

5.archive:

  這種類型只支持select 和 insert語句,並且不支持索引。常應用於日誌記錄和聚合分析方面。

2、存儲引擎如何選擇

  • 是否支持事務
  • 檢索和添加速度
  • 鎖機制
  • 緩存
  • 是否支持全文索引
  • 是否支持外鍵

3、MyISAM和InnoDB對比

  

4、何時使用MyISAM和InnoDB

  MyISAM:讀事務要求不高,以查詢和插入爲主,可使用這個引擎來建立表,例如各類統計表。

  InnoDB:對事務要求高,保存的是重要的數據,例如交易數據,支付數據等,對用戶重要的數據,建議使用InnoDB。

5、對存儲引擎的操做

1.查看數據庫默認的存儲引擎:show engines;   或者  show variables like 'default_storage_engine';

   

   

2.查看錶的存儲引擎:

  1) 顯示錶的建立語句:show create table tablename;

     

  2) 顯示錶的當前狀態值:show table status like ‘tablename’ \G

   

  3) 設置或修改表的存儲引擎

  • 建立數據庫表時設置存儲存儲引擎的基本語法是:

    create table tableName(

      columnName(列名1) type(數據類型) attri(屬性設置),

      columnName(列名2) type(數據類型) attri(屬性設置),

      ....) engine = engineName

  • 修改存儲引擎,能夠用命令 Alter table tableName engine = engineName

5、配置和數據文件

  1.配置文件默認位置

    Linux: /etc/my.cnf

    Windows: my.ini

  2.數據文件位置

   1) 查看數據文件位置的命令: show variables like '%datadir%' ;

   2) 數據文件格式:

      InnoDB:frm(存儲的表結構)、ibd(存儲的數據和索引)

      MyISAM:frm(存儲的表結構)、MYD(存儲的數據)、MYI(存儲的索引)

6、數據庫表設計

1.第一範式

  1) 概念:列不可分。每一列都是不可分割的基本數據項。

  2) 例子:假設咱們有一個學生表,字段包括:id,name,age,contact,以下:

    

     當咱們須要根據QQ來查詢學生的時候,就查詢不出,因此以上的設計就不符合1NF。咱們能夠將contact字段拆分爲phone和QQ,以下:

   

  這樣就知足1NF了。

2.第二範式   

  1) 概念:1NF的基礎上面,非主屬性徹底依賴於主關鍵字。

  2) 例子:學生表:(學號, 姓名, 年齡, 課程名稱, 成績, 學分) ,從字段能夠看出,此表聯合主鍵是(學號,課程名稱)。

   存在以下決定關係:

    1:(學號, 課程名稱) → (姓名, 年齡, 成績, 學分)

    2:(課程名稱) → (學分)

    3:(學號) → (姓名, 年齡)

  其中,姓名、年齡、學分是部分依賴於主鍵的,而成績是徹底依賴於主鍵的,存在部分依賴關係,因此不知足第二範式。

  這會形成以下問題:

    (1) 數據冗餘:

      同一門課程由n個學生選修,"學分"就重複n-1次;同一個學生選修了m門課程,姓名和年齡就重複了m-1次。

    (2) 更新異常:

      若調整了某門課程的學分,數據表中全部行的"學分"值都要更新,不然會出現同一門課程學分不一樣的狀況。

    (3) 插入異常:

      假設要開設一門新的課程,暫時尚未人選修。這樣,因爲尚未"學號"關鍵字,課程名稱和學分也沒法記錄入數據 庫。

    (4) 刪除異常:

      假設一批學生已經完成課程的選修,這些選修記錄就應該從數據庫表中刪除。可是,與此同時,課程名稱和學分信息也被刪除了。很顯然,這也會致使插入異常。

  問題就在於存在非主屬性對主鍵的部分依賴。

  解決辦法:把原表(學號, 姓名, 年齡, 課程名稱, 成績, 學分)分紅三個表:

       學生:Student(學號, 姓名, 年齡);

       課程:Course(課程名稱, 學分);

        選課關係:SelectCourse(學號, 課程名稱, 成績)。

3.第三範式

  1) 概念:2NF的基礎上,屬性不依賴於其它非主屬性 , 消除傳遞依賴。第三範式又可描述爲:表中不存在能夠肯定其餘非關鍵字的非關鍵字段。

  2) 例子:學生表:(學號, 姓名, 年齡, 所在學院, 學院地點, 學院電話),主鍵必然是學號。

         因爲主鍵是單一屬性,因此非主屬性徹底依賴於主鍵,因此必然知足第二範式。可是存在以下傳遞依賴:

      (學號) → (所在學院) → (學院地點, 學院電話),

      學院地點 和 學院電話傳遞依賴於學號,而學院地點和學院電話都是非關鍵字段,即表中出現了「某一非關鍵字段能夠肯定出其它非關鍵字段」的狀況,因而違反了第三範式。          

     解決辦法:

    把原表分紅兩個表:

      學生:(學號, 姓名, 年齡, 所在學院);

      學院:(學院, 地點, 電話)。

7、參考:

  http://www.cnblogs.com/gbyukg/archive/2011/11/09/2242271.html

  http://www.cnblogs.com/lina1006/archive/2011/04/29/2032894.html

  http://www.cnblogs.com/ybwang/archive/2010/06/04/1751279.html

相關文章
相關標籤/搜索