動態(tài)網(wǎng)站開發(fā)報告seo推廣優(yōu)化
索引的概念?
在MySQL中,索引是一種數(shù)據(jù)結構,它被用于快速查找、讀取或插入數(shù)據(jù)。索引能夠極大地提高數(shù)據(jù)庫查詢的速度。
索引的工作方式類似于圖書的索引。如果你想在圖書館找到一本書,你可以按照書名進行查找。書名就像是一個索引,它可以快速引導你找到正確的書籍。在數(shù)據(jù)庫中,索引也是同樣的作用。
索引在MySQL中的作用主要有以下幾點:
- 加速查詢:當對數(shù)據(jù)庫進行查詢時,MySQL可以通過索引快速定位到需要的數(shù)據(jù),而不需要掃描整個數(shù)據(jù)庫。
- 排序:如果查詢需要按照某個字段進行排序,索引可以提高排序的效率。
- 分組(GROUP BY):當使用GROUP BY子句時,索引也可以提高分組的速度。
- 限制結果集:索引可以過濾掉不需要的數(shù)據(jù),從而減少需要返回的數(shù)據(jù)量。
需要注意的是,雖然索引可以提高查詢速度,但是它也有一些負面影響。例如,索引需要占用存儲空間,并且在插入、更新、刪除數(shù)據(jù)時,由于需要維護索引,可能會導致一些性能開銷。因此,在設計數(shù)據(jù)庫時,需要根據(jù)實際情況來決定是否需要創(chuàng)建索引,以及在哪些字段上創(chuàng)建索引。
計算機中磁盤的扇區(qū)與磁道--前提
????????扇區(qū),是指磁盤上劃分的區(qū)域。磁盤上的每個磁道被等分為若干個弧段,這些弧段便是磁盤的扇區(qū),硬盤的讀寫以扇區(qū)為基本單位?
????????
? ? ? ? 其實就是一個磁盤被一個一個同心圓劃分為一個個磁道。一個個磁道被分割為一個個扇區(qū),也就是說在這里面的綠色的就是一個扇區(qū)。
? ? ? ? 通常一個扇區(qū)可以存儲可以存放512個字節(jié)的信息,磁盤驅動器在向磁盤讀取和寫入數(shù)據(jù)時,要以扇區(qū)為單位。
索引的核心--減少磁盤io
磁盤io的效率是很慢的
磁盤io是計算機系統(tǒng)中慢的一項工作,所以它會花費大量的時間。這是因為磁盤io操作的性能取決于它的物理結構,而物理結構受到了一些限制。
磁盤io操作的物理操作
磁盤Io操作受到物理限制,因為磁盤是一個物理磁盤,它有一個機械部件,它是由一個電機驅動的這個電機負責把磁盤上的數(shù)據(jù)讀取到內存中。電機的轉速越快,磁盤的io性能就越好。但是由于電機的機械特性,它的轉速是有限的,所以它的性能也有限。
所以如何快速有效的讓磁盤找到對應的物理地址,就是索引的重要概念
索引的底層以及實現(xiàn)機制?
通過圖示和計算來講述和說明數(shù)據(jù)!!!!!!
我們看一下一條數(shù)據(jù)是多大--在mysql中
示例表 t_demo
那么我們可以根據(jù)每個字段的大小判斷出這個表中的一條數(shù)據(jù)是多大。
計算過程為:
這個表中的一條數(shù)據(jù)的大小取決于具體的數(shù)據(jù)。為了計算每列的大小,我們需要知道每個列的數(shù)據(jù)類型和長度。
對于?id
?列,它是一個?int
?類型,通常占用 4 個字節(jié)。
對于?name
?列,它是一個?varchar
?類型,長度可以根據(jù)具體情況變化。如果最大長度為 25,那么平均每個字符的字節(jié)數(shù)取決于具體的字符集。UTF-8 字符集通常占用 1 到 4 個字節(jié)。所以,如果平均每個字符為 2 個字節(jié)(這是一個常見的估算值),那么?name
?列的平均大小為 50 個字節(jié)。
對于?sex
?列,它是一個?int
?類型,通常占用 4 個字節(jié)。
對于?phone
?列,它也是一個?varchar
?類型,長度可以根據(jù)具體情況變化。如果最大長度為 25,那么平均每個字符的字節(jié)數(shù)也取決于具體的字符集。如果平均每個字符為 2 個字節(jié),那么?phone
?列的平均大小為 50 個字節(jié)。
所以,一般來說,一條數(shù)據(jù)的大小大約在 58 到 108 個字節(jié)之間,具體取決于?name
?和?phone
?列的實際字符長度。
每個屬性的具體大小如下:
id
: 4 bytesname
: 可變長度,取決于實際字符長度。平均每個字符占用 2 個字節(jié),所以平均大小為 2 * length。sex
: 4 bytesphone
: 可變長度,取決于實際字符長度。平均每個字符占用 2 個字節(jié),所以平均大小為 2 * length。
注意:是一種估算方法,具體大小取決于實際情況,包括具體的值和字符集等。
示例的一條記錄:
當然:電話號不是真的
INSERT INTO `day1`.`t_demo` (`id`, `name`, `sex`, `phone`) VALUES (1, '阿丹', 1, '16668066369');
這條記錄的大小為:
id
: 4 個字節(jié)name
: '阿丹' 兩個字符,使用 UTF-8 編碼,每個字符占用 3 個字節(jié),所以 '阿丹' 占用 6?個字節(jié)sex
: 1 個字節(jié)phone
: '16668066369' 11個字符,使用 UTF-8 編碼,每個字符占用 3 個字節(jié),所以 '16668066369' 占用 33?個字節(jié)
所以,這條記錄總共占用 4 + 6 + 1 + 33?= 44?個字節(jié)。
其次就可以計算出一個扇區(qū)可以存放多少條這樣的記錄
計算過程為:
一個扇區(qū)是可存放512個字節(jié)。并且一次磁盤的Io是以扇區(qū)為單位的,也就是說如果讀取了三個字節(jié)就是發(fā)生了三次io。
一個扇區(qū)內可存放記錄為:
512/44=11.6363636364
可以計算得出一個扇區(qū)可以存儲11個記錄。
那么如果此時整張表格需要存儲10000(一萬條數(shù)據(jù))計算可得需要的字節(jié)內存為
44*10000=440000字節(jié)
這個時候我要將這些數(shù)據(jù)存放到多少個扇區(qū)?
440000/512=859.375
也就說如果查找的是在表中的最后一條數(shù)據(jù)的話就要去發(fā)生859次io來將指針移動到我們需要查找的數(shù)據(jù)這里。
所以為了減少io索引的概念出現(xiàn)了。
索引表
表結構簡單,指向單個記錄的地址。
在MySQL中,物理地址的數(shù)據(jù)類型取決于存儲引擎和數(shù)據(jù)表的實現(xiàn)方式。一般來說,物理地址可以是整數(shù)類型(INT)或長整型(LONG),具體取決于存儲引擎和數(shù)據(jù)表的設置。
對于InnoDB存儲引擎,物理地址通常存儲在系統(tǒng)表中的某個列中,例如"FIL_PAGE_ADDR"。對于InnoDB的B-tree索引,每個索引項的大小取決于所存儲列的類型和長度。例如,如果索引列是整數(shù)類型(INT),則每個索引項的大小為4字節(jié)。
索引表的作用主要是為了提高數(shù)據(jù)查詢效率,而不是記錄的物理地址。索引表會根據(jù)特定的列(例如主鍵)對數(shù)據(jù)進行排序,并在每個記錄中存儲相應的物理地址。當執(zhí)行查詢時,MySQL可以通過索引表快速定位到所需的數(shù)據(jù),而不必掃描整個表。
索引表可以是基于B-tree(B樹)或哈希表等數(shù)據(jù)結構實現(xiàn)的。在B-tree索引中,每個節(jié)點包含鍵值和相應的物理地址。根據(jù)鍵值在樹中進行二分查找,可以快速找到相應的記錄。
然而,不同的存儲引擎對索引的實現(xiàn)方式可能會有所不同。例如,InnoDB存儲引擎支持聚集索引(聚集在物理上的索引),這意味著表中的數(shù)據(jù)按照一定順序存儲,并且主鍵索引可以直接提供物理地址。而MyISAM存儲引擎則使用非聚集索引,這意味著索引和數(shù)據(jù)存儲在不同的文件中,需要通過索引獲得中間結果集,然后再根據(jù)結果集中的記錄再回表獲取對應的實際數(shù)據(jù)。
總之,索引表主要用于提高查詢效率,它存儲的是記錄的鍵值和相應的物理地址,而不是記錄的全部信息。
那么關于mysql中的其他索引
在MySQL中,索引和索引表是兩個不同的概念。索引是一種數(shù)據(jù)結構,用于快速查找表中的數(shù)據(jù),而索引表則是存儲索引的一種物理結構。
對于主鍵索引,主鍵通常是記錄的唯一標識符,即記錄的Id。在InnoDB存儲引擎中,主鍵索引是默認創(chuàng)建的,當你在創(chuàng)建表時指定了主鍵列,InnoDB會自動創(chuàng)建一個基于該列的B-tree索引。主鍵索引中存儲的是主鍵列的值和相應的物理地址。
對于其他索引,它們是基于表中的其他列創(chuàng)建的。這些索引中存儲的是該列的值和相應的物理地址。與主鍵索引不同的是,這些索引可能包含部分或全部表的數(shù)據(jù),因此它們的大小可能會比主鍵索引大。
總之,在MySQL中,索引和索引表是兩個不同的概念。主鍵索引是基于主鍵列創(chuàng)建的,而其他索引則是基于表中的其他列創(chuàng)建的。無論哪種類型的索引,它們都存儲了相應的物理地址,用于快速定位到所需的數(shù)據(jù)。
也就說更換的是上圖中的索引表中的主鍵也就是id,更換為這個表中的其他值。
比如我要根據(jù)name進行索引,我對這個列添加了所以那么
那為什么索引會快?
????????如果你的主鍵是int
類型,通常會占用4個字節(jié)。對于該索引表中記錄物理地址的long
類型列,一般會占用8個字節(jié)。也就是說,在這種情況下,一條記錄通常會占用12個字節(jié)(4個字節(jié)主鍵 + 8個字節(jié)物理地址)。請注意,這只是一個簡單的估計,實際的存儲空間可能會受到MySQL的存儲引擎以及其他因素的影響!
? ? ? ? 那么我們可以計算一下如果我們根據(jù)這個主鍵的索引表來查找數(shù)據(jù)會減少多少次io
? ? ? ? 首先一個扇區(qū)可以存放的索引表數(shù)據(jù)條數(shù)
????????512/12=42.6666666667
42條數(shù)據(jù)比之前的表中只能存放11條多了31將近三倍。
????????要查找10000條的io次數(shù)為:
????????12*10000/512=234.375
? ? ? ? 可以看到使用了主鍵索引來查找遍歷10000條數(shù)據(jù)的io次數(shù)為234比上面的859少了很多。當然這只是僅僅使用了主鍵索引,在mysql中還有B+樹作為數(shù)據(jù)結構、以及二級索引還會更快。
? ? ? ? 核心減少了io次數(shù)!!!
mysql中的索引?
MySQL支持多種索引類型,包括B-tree索引、哈希索引、位圖索引等。具體支持的索引類型取決于所使用的存儲引擎。
以下是一些常見的MySQL存儲引擎和它們支持的索引類型:
- InnoDB存儲引擎:支持B-tree索引和哈希索引。
- MyISAM存儲引擎:支持B-tree索引,但不支持哈希索引。
- MEMORY存儲引擎:支持哈希索引和B-tree索引。
- MERGE存儲引擎:不支持獨立的索引,而是通過組合多個MyISAM表中的B-tree索引來實現(xiàn)索引功能。
- FEDERATED存儲引擎:不支持獨立的索引,而是通過訪問遠程MySQL服務器上的表來實現(xiàn)索引功能。
其中特殊索引為:
聚合索引是一種特殊類型的索引,它用于加速對數(shù)據(jù)庫表中的數(shù)據(jù)進行查詢。
在MySQL中,聚合索引是基于表的某個列或多個列的值進行創(chuàng)建的。它可以將數(shù)據(jù)按照索引列的值進行排序,并存儲在索引結構中,從而加速查詢。
聚合索引對于查詢性能的提升非常顯著,特別是對于那些經(jīng)常被查詢的列。它能夠大大減少查詢時需要訪問的數(shù)據(jù)量,從而提高查詢效率。
在InnoDB存儲引擎中,默認情況下會創(chuàng)建一個名為"PRIMARY"的聚合索引,該索引基于主鍵列創(chuàng)建。此外,用戶也可以手動創(chuàng)建額外的聚合索引。
需要注意的是,聚合索引的創(chuàng)建和維護都需要消耗一定的存儲空間和計算資源。因此,在選擇要創(chuàng)建聚合索引的列時,需要仔細考慮列的選擇是否能夠帶來足夠的查詢性能提升,并權衡其開銷和收益。
另外,"PageRank"是Google公司為Web頁面設計的專利算法,它通過分析Web頁面之間的鏈接關系來確定每個頁面的重要性。在MySQL中,沒有直接使用"PageRank"算法的聚合索引,但可以通過其他方法實現(xiàn)類似的功能。
除了聚合索引,MySQL還支持其他一些特殊類型的索引,包括:
- 全文索引:用于在文本搜索中加速查詢。MySQL提供了兩種全文索引類型,即MyISAM和InnoDB引擎支持的全文索引。全文索引主要用于基于單詞或短語在文本塊中的位置進行搜索。
- 空間索引(Spatial Index):也稱為R-tree索引,用于加速空間數(shù)據(jù)的查詢??臻g索引主要應用于地理位置數(shù)據(jù)類型,如點、線、多邊形等。
- 哈希索引(Hash Index):基于哈希算法實現(xiàn)的索引,主要用于等值查詢。哈希索引適用于等值查詢,但對于范圍查詢和排序查詢等操作效率較低。
- 位圖索引(Bitmap Index):是一種特殊的位圖數(shù)據(jù)結構,用于表示一組數(shù)據(jù)中某些元素是否存在。位圖索引適用于具有大量唯一值的列,如性別、學歷等。
需要注意的是,這些特殊類型的索引在MySQL中并不是所有存儲引擎都支持的。例如,全文索引和空間索引僅在MyISAM和InnoDB存儲引擎中支持。在使用這些特殊類型的索引時,建議參考MySQL官方文檔以了解更多詳細信息和特定存儲引擎的限制。
拓展/注意:
? ? ? ? 本文章看完之后可以看到,就算引入了索引表的概念,但是終歸還是一個表。還是要找到一個地方去進行存儲。那就還是有多次Io的問題(在數(shù)據(jù)量大的情況下)。
? ? ? ? 于是就引入了數(shù)據(jù)結構樹的概念。