MySQL 數據庫設計總結

規則1:通常狀況能夠選擇MyISAM存儲引擎,若是須要事務支持必須使用InnoDB存儲引擎。mysql

注意:MyISAM存儲引擎 B-tree索引有一個很大的限制:參與一個索引的全部字段的長度之和不能超過1000字節。另外MyISAM數據和索引是分開,而InnoDB的數據存儲是按聚簇(cluster)索引有序排列的,主鍵是默認的聚簇(cluster)索引,所以MyISAM雖然在通常狀況下,查詢性能比InnoDB高,但InnoDB的以主鍵爲條件的查詢性能是很是高的。spring

規則2:命名規則。sql

  1. 數據庫和表名應儘量和所服務的業務模塊名一致
  2. 服務與同一個子模塊的一類表應儘可能以子模塊名(或部分單詞)爲前綴或後綴
  3. 表名應儘可能包含與所存放數據對應的單詞
  4. 字段名稱也應儘可能保持和實際數據相對應
  5. 聯合索引名稱應儘可能包含全部索引鍵字段名或縮寫,且各字段名在索引名中的順序應與索引鍵在索引中的索引順序一致,並儘可能包含一個相似idx的前綴或後綴,以代表期對象類型是索引。
  6. 約束等其餘對象也應該儘量包含所屬表或其餘對象的名稱,以代表各自的關係

規則3:數據庫字段類型定義數據庫

  1. 常常須要計算和排序等消耗CPU的字段,應該儘可能選擇更爲迅速的字段,如用TIMESTAMP(4個字節,最小值1970-01-0100:00:00)代替Datetime(8個字節,最小值1001-01-01 00:00:00),經過整型替代浮點型和字符型
  2. 變長字段使用varchar,不要使用char
  3. 對於二進制多媒體數據,流水隊列數據(如日誌),超大文本數據不要放在數據庫字段中

規則4:業務邏輯執行過程必須讀到的表中必需要有初始的值。避免業務讀出爲負或無窮大的值致使程序失敗緩存

規則5:並不須要必定遵照範式理論,適度的冗餘,讓Query儘可能減小Join性能優化

規則6:訪問頻率較低的大字段拆分出數據表。有些大字段佔用空間多,訪問頻率較其餘字段明顯要少不少,這種狀況進行拆分,頻繁的查詢中就不須要讀取大字段,形成IO資源的浪費。微信

規則7:大表能夠考慮水平拆分。大表影響查詢效率,根據業務特性有不少拆分方式,像根據時間遞增的數據,能夠根據時間來分。以id劃分的數據,可根據id%數據庫個數的方式來拆分。架構

一.數據庫索引

規則8:業務須要的相關索引是根據實際的設計所構造sql語句的where條件來肯定的,業務不須要的不要建索引,不容許在聯合索引(或主鍵)中存在多於的字段。特別是該字段根本不會在條件語句中出現。併發

規則9:惟一肯定一條記錄的一個字段或多個字段要創建主鍵或者惟一索引,不能惟一肯定一條記錄,爲了提升查詢效率建普通索引分佈式

規則10:業務使用的表,有些記錄數不多,甚至只有一條記錄,爲了約束的須要,也要創建索引或者設置主鍵。

規則11:對於取值不能重複,常常做爲查詢條件的字段,應該建惟一索引(主鍵默認惟一索引),而且將查詢條件中該字段的條件置於第一個位置。沒有必要再創建與該字段有關的聯合索引。

規則12:對於常常查詢的字段,其值不惟一,也應該考慮創建普通索引,查詢語句中該字段條件置於第一個位置,對聯合索引處理的方法一樣。

規則13:業務經過不惟一索引訪問數據時,須要考慮經過該索引值返回的記錄稠密度,原則上可能的稠密度最大不能高於0.2,若是稠密度太大,則不合適創建索引了。

當經過這個索引查找獲得的數據量佔到表內全部數據的20%以上時,則須要考慮創建該索引的代價,同時因爲索引掃描產生的都是隨機I/O,生其效率比全表順序掃描的順序I/O低不少。數據庫系統優化query的時候有可能不會用到這個索引。

規則14:須要聯合索引(或聯合主鍵)的數據庫要注意索引的順序。SQL語句中的匹配條件也要跟索引的順序保持一致。

注意:索引的順勢不正確也可能致使嚴重的後果。

規則15:表中的多個字段查詢做爲查詢條件,不含有其餘索引,而且字段聯合值不重複,能夠在這多個字段上建惟一的聯合索引,假設索引字段爲 (a1,a2,...an),則查詢條件(a1 op val1,a2 op val2,...am op valm)m<=n,能夠用到索引,查詢條件中字段的位置與索引中的字段位置是一致的。

規則16:聯合索引的創建原則(如下均假設在數據庫表的字段a,b,c上創建聯合索引(a,b,c))

  1. 聯合索引中的字段應儘可能知足過濾數據從多到少的順序,也就是說差別最大的字段應該房子第一個字段
  2. 創建索引儘可能與SQL語句的條件順序一致,使SQL語句儘可能以整個索引爲條件,儘可能避免以索引的一部分(特別是首個條件與索引的首個字段不一致時)做爲查詢的條件
  3. Where a=1,where a>=12 and a<15,where a=1 and b<5 ,where a=1 and b=7
    and c>=40爲條件能夠用到此聯合索引;而這些語句where b=10,where c=221,where b>=12 andc=2則沒法用到這個聯合索引。
  4. 當須要查詢的數據庫字段所有在索引中體現時,數據庫能夠直接查詢索引獲得查詢信息無須對整個表進行掃描(這就是所謂的key-only),能大大的提升查詢效率。當a,ab,abc與其餘表字段關聯查詢時能夠用到索引
  5. 當a,ab,abc順序而不是b,c,bc,ac爲順序執行Order by或者group不要時能夠用到索引
  6. 如下狀況時,進行表掃描而後排序可能比使用聯合索引更加有效
    a.表已經按照索引組織好了
    b.被查詢的數據站全部數據的不少比例。

規則17:重要業務訪問數據表時。但不能經過索引訪問數據時,應該確保順序訪問的記錄數目是有限的,原則上不得多於10.

二.Query語句與應用系統優化

規則18:合理構造Query語句

  1. Insert語句中,根據測試,批量一次插入1000條時效率最高,多於1000條時,要拆分,屢次進行一樣的插入,應該合併批量進行。注意query語句的長度要小於mysqld的參數max_allowed_packet
  2. 查詢條件中各類邏輯操做符性能順序是and,or,in,所以在查詢條件中應該儘可能避免使用在大集合中使用in
  3. 永遠用小結果集驅動大記錄集,由於在mysql中,只有NestedJoin一種Join方式,就是說mysql的join是經過嵌套循環來實現的。經過小結果集驅動大記錄集這個原則來減小嵌套循環的循環次數,以減小IO總量及CPU運算次數
  4. 儘可能優化Nested Join內層循環。
  5. 只取須要的columns,儘可能不要使用select *
  6. 僅僅使用最有效的過濾字段,where 字句中的過濾條件少爲好
  7. 儘可能避免複雜的Join和子查詢

Mysql在併發這塊作得並非太好,當併發量過高的時候,總體性能會急劇降低,這主要與Mysql 內部資源的爭用鎖定控制有關,MyIsam用表鎖,InnoDB好一些用行鎖。

規則19:應用系統的優化
一、 合理使用cache,對於變化較少的部分活躍數據經過應用層的cache緩存到內存中,對性能的提高是成數量級的。
二、 對重複執行相同的query進行合併,減小IO次數。
三、 事務相關性最小原則

在此我向你們推薦一個架構學習交流羣。交流學習羣號:478030634 裏面會分享一些資深架構師錄製的視頻錄像:有Spring,MyBatis,Netty源碼分析,高併發、高性能、分佈式、微服務架構的原理,JVM性能優化、分佈式架構等這些成爲架構師必備的知識體系。還能領取免費的學習資源,目前受益良多

注:關注做者微信公衆號,瞭解更多分佈式架構、微服務、netty、MySQL、spring、性能優化、等知識點。公衆號:《Java爛豬皮》
圖片描述

相關文章
相關標籤/搜索