欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

MySQL數(shù)據(jù)表分區(qū)策略及優(yōu)缺點分析

 更新時間:2021年05月17日 10:49:39   作者:島上碼農(nóng)  
項目開發(fā)中,隨著數(shù)據(jù)庫數(shù)據(jù)量越來越大,單個表中數(shù)據(jù)太多,從而導致查詢速度變慢,而且由于表的鎖機制導致應用操作也受到嚴重影響,出現(xiàn)了數(shù)據(jù)庫性能瓶頸。因此我們需要考慮分表與分區(qū),MySQL分表分區(qū)就是為了解決大數(shù)據(jù)量導致MySQL性能低下的問題。

為什么需要分區(qū)?

當面對巨大的數(shù)據(jù)表的時候,至少有一件事情是確定的,表太大了以至于每次查詢的時候我們沒法做全表掃描。而這個時候也沒法使用索引,或者說索引意義不大,更不用說索引的維護代價和空間占用非常高。如果是依賴索引,會導致大量的碎片和低聚集度的數(shù)據(jù),這會導致查詢的時候有上千次的隨機 I/O 訪問而導致宕機。這種情況下一般只會使用1-2個索引,而不會更多。這種情況下,有兩個可行的選項:查詢必須從數(shù)據(jù)表的指定的部分順序查找或者是期望的部分數(shù)據(jù)及其索引與服務器的內(nèi)存匹配。

需要再次重申:在存儲空間過大時,除非索引覆蓋了整個查詢,否則二叉樹索引就無法發(fā)揮作用。服務端需要查找數(shù)據(jù)表的一整行數(shù)據(jù),并且會在一個大空間跨度里執(zhí)行隨機 I/O 操作,這會導致查詢響應時間無法接受。而維護索引(磁盤空間,I/O 操作)的代價同樣很高。

而這是分區(qū)能夠解決的問題。這其中的關鍵就是分區(qū)是索引的一個初級形式,它的負荷低并且能夠讓我們從臨近的數(shù)據(jù)中獲取結(jié)果。這種情形下,我們可以依次掃描相鄰的數(shù)據(jù)或者是將臨近的數(shù)據(jù)加載到內(nèi)存進行檢索。分區(qū)之所以負荷低是因為它并沒有指針指向?qū)臄?shù)據(jù)行,也不需要被更新。分區(qū)并不精確地將數(shù)據(jù)按行劃分,也沒有涉及到所謂的數(shù)據(jù)結(jié)構(gòu)。實際上,分區(qū)相當于對數(shù)據(jù)進行了分類。

分區(qū)的策略

對于大數(shù)據(jù)表,有兩種策略進行分區(qū):

  • 不使用索引:創(chuàng)建數(shù)據(jù)表時不增加索引,而是使用分區(qū)定位到所需要的數(shù)據(jù)行。只要你使用 WHERE 條件將查詢切分到很小的分區(qū)范圍,就已經(jīng)足夠了。這個時候需要通過數(shù)學方法計算查詢的響應時間是否能夠接受。當然,這里的假設是不會將數(shù)據(jù)放到內(nèi)存中,而是全部數(shù)據(jù)都從磁盤讀取。因此數(shù)據(jù)很快就會被其他查詢覆蓋,使用緩存沒什么意義。這種情況一般用于大量數(shù)據(jù)表的基數(shù)是常規(guī)的。需要注意的是,需要限制分區(qū)數(shù)在幾百。
  • 使用索引,并且隔離熱區(qū)數(shù)據(jù):如果除了熱區(qū)數(shù)據(jù)外,大部分數(shù)據(jù)是不使用的,則可以將熱區(qū)數(shù)據(jù)單獨的分區(qū),這個分區(qū)算上索引都能夠加載到內(nèi)存中。這個時候可以通過索引來優(yōu)化性能,就像操作普通的數(shù)據(jù)表一樣。

分區(qū)隱患

兩種分區(qū)策略是基于兩個關鍵假設:在查詢的時候可以通過過濾分區(qū)縮小查找范圍,且分區(qū)自身的代價不高。然而,這兩個假設未必總是有效,下面是可能遇到的問題:

  • NULL 空值可能導致分區(qū)過濾失效:當分區(qū)函數(shù)可能是 NULL 時,分區(qū)工作的結(jié)果就會很奇特。它會假設第一個分區(qū)是特殊的。假設使用 PARTITION BY RANGE YEAR(order_date)這樣的分區(qū)方法,如果 order_date 這個列是 NULL 或者無效的日期都會存儲在第一個分區(qū)。假設寫了一個查詢使用了這樣的查詢條件 :WHERE order_date BETWEEN '2021-01-01' AND '2021-01-31'。MySQL 實際上會檢查2個分區(qū),一個是 YEAR 這個函數(shù) 在接收到無效輸入時可能會返回 NULL,另一個是符合條件的值可能是 NULL(存儲在第一個分區(qū)中)。這種情況對其他函數(shù)也可能,例如 TO_DAYS。如果第一個分區(qū)很大的話,就會產(chǎn)生問題,尤其是使用第一種不使用索引策略時。從兩個分區(qū)查找數(shù)據(jù)而不是一個分區(qū)的效果是完全意外的。為了避免這種情況,應該創(chuàng)造“假的”第一分區(qū),例如 PARTITION p_nulls VALUES LESS THAN (0)。如果沒有無效數(shù)據(jù)存入數(shù)據(jù)表的話,這個第一分區(qū)將是空的,即便它也會被掃描,但是因為是空的或者數(shù)據(jù)量很少,對性能影響不大。這種情況在 MySQL 5.5以后,如果直接使用列進行分區(qū)的話就不需要處理,但是如果是使用函數(shù)的話就要這樣做。
  • 索引與分區(qū)不匹配:假設定義了一個索引與分區(qū)條件不匹配,查詢就可能無法對分區(qū)進行過濾。假設定義了 字段 a 的索引卻使用 字段 b 進行分區(qū)。由于每個分區(qū)都會有自己的索引,針對這個索引的查詢會遍歷所有分區(qū)的索引樹。如果索引樹的非葉子節(jié)點都常駐內(nèi)存查詢起來還比較快,但是也沒法避免全部索引的掃描。為了避免這種情況,應當盡量避免使用非分區(qū)的索引列,除非WHERE 條件本身能夠指定分區(qū)??雌饋磉@樣很容易避免,實際上卻令人吃驚。例如,假設一個分區(qū)表用在第二個表查詢聯(lián)合查詢后,而聯(lián)合查詢使用的索引并不是分區(qū)的索引。則聯(lián)合查詢的每一行都會訪問和掃碼第二張表的分區(qū)。
  • 決定使用哪個分區(qū)代價可能很高:分區(qū)實現(xiàn)的方式各有差異,因此實際的性能并不總是一致。特別是當遇到“這個數(shù)據(jù)行屬于哪個分區(qū)”或者“如何才能查找到與查詢條件匹配的數(shù)據(jù)行”這樣的問題時。在眾多分區(qū)的情況下來回答這樣的問題很費勁。線性搜索并不總是那么有效,結(jié)果是隨著分區(qū)數(shù)的增長代價也在上升。最為糟糕的形式是逐行插入。每次插入一行數(shù)據(jù)到分區(qū)的數(shù)據(jù)表,服務器都需要掃描一次使用哪個分區(qū)存放新的數(shù)據(jù)行??梢酝ㄟ^限制分區(qū)的數(shù)量來減輕這個問題,事實上,一般不建議超過100個分區(qū)。當然,對于其他分區(qū)類型,如鍵值和哈希分區(qū)則不會有這樣的限制。
  • 打開和鎖定分區(qū)代價也可能很高:分區(qū)表帶來的一個負面效應是查詢時需要對每個分區(qū)進行打開和鎖定。而這個過程是在過濾分區(qū)前進行的。這個代價與分區(qū)類型無關,且會影響所有的操作語句。這種影響對于短數(shù)據(jù)量的查詢尤其明顯,例如只查詢一行數(shù)據(jù)時。這種缺陷可以通過批量操作替代單次來降低,例如一次插入多行,或 LOAD DATA INFILE,一次按范圍刪除數(shù)據(jù)等等。當然,限制分區(qū)的數(shù)量也是有效的。
  • 維護操作代價可能很高:有些分區(qū)的維護是很快的,例如創(chuàng)建或者刪除分區(qū)。而其他操作,例如調(diào)整分區(qū),就有點像 ALTER 對表的操作那樣了:需要循環(huán)復制數(shù)據(jù)行。例如,調(diào)整分區(qū)會創(chuàng)建一個臨時分區(qū),然后將數(shù)據(jù)移入到新的分區(qū),再刪除舊的分區(qū)。

如上所述,分區(qū)并不是完美解決方案,目前版本的 MySQL還有一些其他的約束:

  • 所有分區(qū)必須使用相同的存儲引擎。
  • 分區(qū)函數(shù)能夠選用的函數(shù)或表達式有一定的限制。
  • 有些存儲引擎并不支持分區(qū)。
  • 對于 MYISAM 數(shù)據(jù)表,無法使用 LOAD INDEX INTO CACHE。
  • 對于 MYISAM 數(shù)據(jù)表,分區(qū)表需要更多的打開文件描述符,這意味著單個數(shù)據(jù)表的緩存入口可能對應多個文件描述符。因此基本配置限制了數(shù)據(jù)表的緩存以避免超出服務器操作系統(tǒng)的預處理量,而分區(qū)表可能導致實際超出這個限制。

當然,隨著 MySQL 版本的更新迭代,對分區(qū)的支持也越來越好,并且很多分區(qū)的問題都得到了修復。

以上就是MySQL數(shù)據(jù)表分區(qū)策略及優(yōu)缺點分析的詳細內(nèi)容,更多關于MySQL數(shù)據(jù)表分區(qū)策略及優(yōu)缺點的資料請關注腳本之家其它相關文章!

相關文章

  • MySQL排序中使用CASE WHEN的方法示例

    MySQL排序中使用CASE WHEN的方法示例

    這篇文章主要給大家介紹了關于MySQL排序中使用CASE WHEN的相關資料,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2019-01-01
  • 解決MySQL Workbench gnome-keyring-daemon錯誤的方法分享

    解決MySQL Workbench gnome-keyring-daemon錯誤的方法分享

    這篇文章主要介紹了解決MySQL Workbench gnome-keyring-daemon錯誤的方法,需要的朋友可以參考下
    2014-08-08
  • /var/log/pacct文件導致MySQL啟動失敗的案例分享

    /var/log/pacct文件導致MySQL啟動失敗的案例分享

    這篇文章主要介紹了/var/log/pacct文件導致MySQL啟動失敗的案例分享,這是個比較讓人郁悶的問題,找不到MySQL啟動失敗的原因進可以按此文的方法試一試,需要的朋友可以參考下
    2015-01-01
  • Mysql事務中Update是否會鎖表?

    Mysql事務中Update是否會鎖表?

    這篇文章主要給大家介紹了關于Mysql事務中Update是否會鎖表的相關資料,文中通過示例代碼介紹的非常詳細,對大家的學習或者工作具有一定的參考學習價值,需要的朋友們下面隨著小編來一起學習學習吧
    2020-12-12
  • 關于MySQL中explain工具的使用

    關于MySQL中explain工具的使用

    這篇文章主要介紹了關于MySQL中explain工具的使用,在select語句之前增加explain關鍵字,MySQL會在查詢上設置一個標記,執(zhí)行查詢會返回執(zhí)行計劃的信息,而不是執(zhí)行這條SQL,需要的朋友可以參考下
    2023-05-05
  • MYSQL METADATA LOCK(MDL LOCK) 理論及加鎖類型測試

    MYSQL METADATA LOCK(MDL LOCK) 理論及加鎖類型測試

    這篇文章主要介紹了MYSQL METADATA LOCK(MDL LOCK)的內(nèi)容,有理論知識和加鎖類型測試的以下代碼,感興趣的朋友請參考下午文
    2021-09-09
  • Linux中部署MySQL環(huán)境的四種方式圖文詳解

    Linux中部署MySQL環(huán)境的四種方式圖文詳解

    這篇文章主要介紹了Linux中部署MySQL環(huán)境的四種方式,本文通過圖文并茂的形式給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友參考下吧
    2023-11-11
  • Mysql啟動報ERROR:2002的分析與解決

    Mysql啟動報ERROR:2002的分析與解決

    這篇文章主要給大家介紹了關于Mysql啟動時報ERROR:2002問題的分析與解決方法,文中通過示例代碼介紹將該問題分析的非常詳細,對同樣遇到這個問題的朋友們具有一定的參考學習價值,需要的朋友們下面來一起看看吧。
    2017-08-08
  • 連接mysql報錯——沒有設置“usessl=false”的問題

    連接mysql報錯——沒有設置“usessl=false”的問題

    這篇文章主要介紹了連接mysql報錯——沒有設置“usessl=false”的問題及解決方案,具有很好的參考價值,希望對大家有所幫助。如有錯誤或未考慮完全的地方,望不吝賜教
    2022-08-08
  • 解決Navicat Premium 連接 MySQL 8.0 報錯

    解決Navicat Premium 連接 MySQL 8.0 報錯"1251"的問題分析

    這篇文章主要介紹了解決Navicat Premium 連接 MySQL 8.0 報錯"1251"的問題分析,本文通過圖文并茂的形式給大家介紹的非常詳細,對大家的學習或工作具有一定的參考借鑒價值,需要的朋友可以參考下
    2020-11-11

最新評論