mysql的水平拆分和垂直拆分
1,水平分割:
例:QQ的登入表。假設QQ的使用者有100億,如果只有一張表,每個使用者登入的時候資料庫都要從這100億中查詢,會很慢很慢。如果將這一張表分成100份,每張表有1億條,就小了很多,比如qq0,qq1,qq1...qq99表。
使用者登入的時候,可以將使用者的id%100,那麼會得到0-99的數,查詢表的時候,將表名qq跟取模的數連線起來,就構建了表名。比如123456789使用者,取模的89,那麼就到qq89表查詢,查詢的時間將會大大縮短。
這就是水平分割。
2,垂直分割:
垂直分割指的是:表的記錄並不多,但是欄位卻很長,表佔用空間很大,檢索表的時候需要執行大量的IO,嚴重降低了效能。這時需要把大的欄位拆分到另一個表,並且該表與原表是一對一的關係。
例如學生答題表tt:有如下欄位:
Id name 分數 題目 回答
其中題目和回答是比較大的欄位,id name 分數比較小。
如果我們只想查詢id為8的學生的分數:select 分數 from tt where id = 8;雖然知識查詢分數,但是題目和回答這兩個大欄位也是要被掃描的,很消耗效能。但是我們只關心分數,並不想查詢題目和回答。這就可以使用垂直分割。我們可以把題目單獨放到一張表中,通過id與tt表建立一對一的關係,同樣將回答單獨放到一張表中。這樣我們插敘tt中的分數的時候就不會掃描題目和回答了。
3,其他要點:
1)存放圖片、檔案等大檔案用檔案系統儲存。資料庫只儲存路徑,圖片和檔案存放在檔案系統,甚至單獨存放在一臺伺服器(圖床)。
2)資料引數配置。
最重要的引數就是記憶體,我們主要用的innodb引擎,所以下面兩個引數調的很大:
innodb_additional_mem_pool_size=64M
innodb_buffer_pool_size=1G
對於MyISAM,需要調整key_buffer_size,當然調整引數還是要看狀態,用show status語句可以看到當前狀態,以決定該調整哪些引數。
4,合理的硬體資源和作業系統
如果機器的記憶體超過4G,那麼應當採用64位作業系統和64位MySQL。
案例:
簡單購物系統暫設涉及如下表:
1.產品表(資料量10w,穩定)
2.訂單表(資料量200w,且有增長趨勢)
3.使用者表 (資料量100w,且有增長趨勢)
以mysql為例講述下水平拆分和垂直拆分,mysql能容忍的數量級在百萬靜態資料可以到千萬
垂直拆分:
解決問題:
表與表之間的io競爭
不解決問題:
單表中資料量增長出現的壓力
方案:
把產品表和使用者表放到一個server上
訂單表單獨放到一個server上
水平拆分:
解決問題:
單表中資料量增長出現的壓力
不解決問題:
表與表之間的io爭奪
方案:
使用者表通過性別拆分為男使用者表和女使用者表
訂單表通過已完成和完成中拆分為已完成訂單和未完成訂單
產品表 未完成訂單放一個server上
已完成訂單表盒男使用者表放一個server上
女使用者表放一個server上
實際操作:
$_GET['id'] = 17, 17%4 + 1 = 2, $tableName = 'users'.'2' Select * from users2 where id = 17; 在insert時還需要一張臨時表uid_temp來提供自增的ID,該表的唯一用處就是提供自增的ID; insert into uid_temp values(null); 得到自增的ID後,又通過取模法進行分表插入; 注意,進行水平拆分後的表,欄位的列和型別和原表應該是相同的,但是要記得去掉auto_increment自增長