如何理解MySQL數(shù)據(jù)庫Innodb內(nèi)存結(jié)構(gòu)以及怎樣使用內(nèi)存的

如何理解MySQL數(shù)據(jù)庫Innodb內(nèi)存結(jié)構(gòu)以及怎樣使用內(nèi)存的,針對這個問題,這篇文章詳細(xì)介紹了相對應(yīng)的分析和解答,希望可以幫助更多想解決這個問題的小伙伴找到更簡單易行的方法。

10余年的寧國網(wǎng)站建設(shè)經(jīng)驗,針對設(shè)計、前端、開發(fā)、售后、文案、推廣等六對一服務(wù),響應(yīng)快,48小時及時工作處理。成都全網(wǎng)營銷推廣的優(yōu)勢是能夠根據(jù)用戶設(shè)備顯示端的尺寸不同,自動調(diào)整寧國建站的顯示方式,使網(wǎng)站能夠適用不同顯示終端,在瀏覽器中調(diào)整網(wǎng)站的寬度,無論在任何一種瀏覽器上瀏覽網(wǎng)站,都能展現(xiàn)優(yōu)雅布局與設(shè)計,從而大程度地提升瀏覽體驗。成都創(chuàng)新互聯(lián)公司從事“寧國網(wǎng)站設(shè)計”,“寧國網(wǎng)站推廣”以來,每個客戶項目都認(rèn)真落實執(zhí)行。

概述

很多朋友可能會有許多關(guān)于Innodb如何使用內(nèi)存的問題。我這里將簡單介紹一下innodb內(nèi)存結(jié)構(gòu),然后以innodb啟動時的分配情況做一個解釋。

如何理解MySQL數(shù)據(jù)庫Innodb內(nèi)存結(jié)構(gòu)以及怎樣使用內(nèi)存的

1. INNODB內(nèi)存結(jié)構(gòu)

如何理解MySQL數(shù)據(jù)庫Innodb內(nèi)存結(jié)構(gòu)以及怎樣使用內(nèi)存的

(1) 聚集索引與非聚集索引:

聚集索引:主鍵,有序,存儲順序與內(nèi)存一致

非聚集索引:非主鍵,無序

  • 聚集索引在葉子節(jié)點存儲的是表中的數(shù)據(jù)

  • 非聚集索引在葉子節(jié)點存儲的是主鍵和索引列

  • 使用非聚集索引查詢出數(shù)據(jù)時,拿到葉子上的主鍵再去查到想要查找的數(shù)據(jù)。(拿到主鍵再查找這個過程叫做回表)

(2) 緩沖池:

緩沖池用于存放各種數(shù)據(jù)的緩存。Innodb總是將磁盤中的數(shù)據(jù)(數(shù)據(jù)庫文件)按頁(16K)讀取到緩沖池,然后按最近最少使用算法(LRU)來保存緩沖池中的數(shù)據(jù)。

如果數(shù)據(jù)庫文件需要修改,總是先修改在緩存池中的頁(發(fā)生修改后,該頁為臟頁),然后按一定頻率刷新到磁盤中。

(3) insert buffer(插入緩沖):

使用條件:1.索引是輔助索引;2.索引不是唯一的。

也就是說,主鍵索引不使用插入緩沖。主鍵索引是聚集索引,插入是順序的,執(zhí)行效率比較高,就不借助緩沖了。

但是,當(dāng)表中存在輔助索引(非聚集索引,非主鍵)時,不一定是順序的了,這時需要離散的訪問,插入性能會降低。

所以,對于非聚集索引的插入和更新操作,不是直接插入到索引頁中,而是插入到緩沖中,再以一定頻率執(zhí)行插入緩沖和非聚集索引葉子節(jié)點的合并操作。

注:由于非主鍵索引葉子節(jié)點存的是主鍵和當(dāng)前列值,所以使用非聚集索引查詢時,先查輔助索引的那顆樹找到對應(yīng)的主鍵,再查主鍵索引的那顆樹,會查兩次,效率不高。

(4) redo log(重做日志):

在事務(wù)提交的時候,Innodb會先把數(shù)據(jù)從磁盤中讀到內(nèi)存進(jìn)行修改,然后把事務(wù)日志寫到日志緩沖(log buffer),然后再刷新到重做日志文件(redo  log file)中進(jìn)行持久化,然后再定期刷新到磁盤中。

用于在實例故障恢復(fù)時,繼續(xù)那些已經(jīng)commit但數(shù)據(jù)尚未完全回寫到磁盤的事務(wù)。

(5) double write(兩次寫):

為防止redo log在寫的過程中損壞,我們需要留個備份。若出現(xiàn)故障,先從備份中恢復(fù)redo log,再進(jìn)行數(shù)據(jù)恢復(fù)。

(6) undo log:

記錄數(shù)據(jù)修改前的鏡像,用于將未提交的事務(wù)回滾到事務(wù)開始前的狀態(tài)。

undo操作:當(dāng)Innodb存儲引擎回滾時,它實際上做的是與之前相關(guān)的工作,對于insert操作,Innodb會完成一個delete,對于update,則會執(zhí)行一個相反的update,將修改前的行放回去。

(7) 自適應(yīng)哈希索引:

Innodb會監(jiān)控表上索引的查找頻率,若發(fā)現(xiàn)建立哈希索引會提升速度,則自動創(chuàng)建哈希索引。不是對整張表建立索引,而是根據(jù)訪問頻率對某些頁建立。

(8) 事務(wù)提交:

事務(wù)進(jìn)行過程中,每次sql語句執(zhí)行,都會記錄undo log和redo log,然后更新數(shù)據(jù)形成臟頁。然后redo  log按照時間或空間等條件進(jìn)行落盤,undo log和臟頁按照checkpoint進(jìn)行落盤,落盤后相應(yīng)的redo  log就可以刪除了。

此時,事務(wù)還未commit,如果發(fā)生崩潰,則首先檢查checkpoint記錄,使用相應(yīng)的redo log進(jìn)行數(shù)據(jù)和undo  log的恢復(fù),然后查看undo log的狀態(tài)發(fā)現(xiàn)事務(wù)尚未提交,然后就使用undo log進(jìn)行回滾。事務(wù)執(zhí)行commit操作時,會將本事務(wù)相關(guān)的所有redo  log都進(jìn)行落盤,只有所有redo  log落盤成功,才算commit成功。

然后內(nèi)存中的數(shù)據(jù)臟頁繼續(xù)按照checkpoint進(jìn)行落盤。如果此時發(fā)生了崩潰,則只使用redo log恢復(fù)數(shù)據(jù)。

2. 一些重要的概念:

  • NBLOCKS=Innodb_buffer_pool有多個頁(block)=innodb_buffer_pool_size/16384(16k)

  • OS_THREADS= if ( innodb_buffer_pool_size >= 1000Mb) = 50000

  • else if (innodb_buffer_pool_size >= 8Mb) = 10000

  • else = 1000 (該值只用在*nixes系統(tǒng)上,對于Windows有一點小的區(qū)別計算OS_THREADS)

3. Innodb 使用的內(nèi)存包括:

如何理解MySQL數(shù)據(jù)庫Innodb內(nèi)存結(jié)構(gòu)以及怎樣使用內(nèi)存的

  • innodb_buffer_pool_size

  • innodb_additional_mem_pool_size

  • innodb_log_buffer_size

  • adaptive index hash ,size (innodb buffer 索引管理區(qū))=  innodb_buffer_pool_size/64

  • system dictionary hash,size(innodb內(nèi)部字典區(qū)) = 6 *  innodb_buffer_pool_size/512

  • memory for sync_array,size(用于Innodb內(nèi)部syncronzation的開銷)=OS_THREAD * 512

  • memory for os_event,size(用于innodb內(nèi)存的syncronzation的開銷)=OS_THREAD * 216

  • memory for locking system(內(nèi)存的鎖管理系統(tǒng)),size = 5 * 4 *NBBLOCKS

4. innodb內(nèi)存使用的計算公式為:

Innodb_buffer_pool_size + innodb_log_buffer_size + innodb_additional_mem_pool_size + 812/16384 * innodb_buffer_pool_size + OS_THREADS * 368

對于812/16384 * Innodb_buffer_pool_size 可以簡單的用 innodb_buffer_pool_size /  20 計算,對于OS_THREADS * 368

OS_THREADS * 368 = 17.5 MB if innodb_buffer_pool_size > 1000MB OS_THREADS * 3368 = 3.5 MB if innodb_buffer_pool_size > 8MB

舉一個例子:

如果你的innodb_buffer_pool_size有1500MB,innodb_additional_mem_pool_size =20  MB,innodb_log_buffer_size = 8M,

Innodb 將會向系統(tǒng)申請內(nèi)存為= 1500M + 20M + 8M + 1500/20 M +17.5 = 1620.5M

根據(jù)以上的條件可以算出Innodb最根本最需要多少內(nèi)存,這樣對于服務(wù)器的內(nèi)存使用也可以有一個規(guī)劃了。

關(guān)于如何理解MySQL數(shù)據(jù)庫Innodb內(nèi)存結(jié)構(gòu)以及怎樣使用內(nèi)存的問題的解答就分享到這里了,希望以上內(nèi)容可以對大家有一定的幫助,如果你還有很多疑惑沒有解開,可以關(guān)注創(chuàng)新互聯(lián)行業(yè)資訊頻道了解更多相關(guān)知識。

網(wǎng)頁標(biāo)題:如何理解MySQL數(shù)據(jù)庫Innodb內(nèi)存結(jié)構(gòu)以及怎樣使用內(nèi)存的
鏈接分享:http://bm7419.com/article18/pscggp.html

成都網(wǎng)站建設(shè)公司_創(chuàng)新互聯(lián),為您提供微信小程序、手機網(wǎng)站建設(shè)、外貿(mào)建站、、關(guān)鍵詞優(yōu)化、企業(yè)網(wǎng)站制作

廣告

聲明:本網(wǎng)站發(fā)布的內(nèi)容(圖片、視頻和文字)以用戶投稿、用戶轉(zhuǎn)載內(nèi)容為主,如果涉及侵權(quán)請盡快告知,我們將會在第一時間刪除。文章觀點不代表本網(wǎng)站立場,如需處理請聯(lián)系客服。電話:028-86922220;郵箱:631063699@qq.com。內(nèi)容未經(jīng)允許不得轉(zhuǎn)載,或轉(zhuǎn)載時需注明來源: 創(chuàng)新互聯(lián)

成都做網(wǎng)站