mysql優化概述3

weixin_33896726發表於2017-01-17
1、字首索引
建立索引關鍵字一種方案。
通常會使用欄位的整體作為索引關鍵字。
有時,使用欄位前部分資料,也可以去識別某些記錄。
語法:
index `索引名` (`欄位`(N)); 使用欄位前N個字元建立索引。
N,究竟是多少? 
使用N長度所達到的辯識度,極限接近於使用全部長度的辯識度概可。
> select count(*) from student; --總記錄數,比如1000000
> select 1000000/count(distinct ename) from student; --ename能夠達到的最大辯識度
> select 1000000/count(distinct substring(ename, 1, 5)) from student; --測試前5個字元達到的辯識度
依次取前N個字元,進行對比,找到極限接近辯識度的長度。

> alter table student add index `i_ename` (`ename`(9));
(*字首索引不能使用索引覆蓋。)

2、全文索引
特殊:關鍵字的建立上。
為了解決like '%keyword%'這類查詢的匹配問題。

表結構如下:
CREATE TABLE articles (
    id INT UNSIGNED AUTO_INCREMENT NOT NULL PRIMARY KEY,
    title VARCHAR(200),
    body TEXT
);

INSERT INTO articles (title,body) VALUES
('MySQL Tutorial','DBMS stands for DataBase ...'),
('How To Use MySQL Well','After you went through a ...'),
('Optimizing MySQL','In this tutorial we will show ...'),
('1001 MySQL Tricks','1. Never run mysqld as root. 2. ...'),
('MySQL vs. YourSQL','In the following database comparison ...'),
('MySQL Security','When configured properly, MySQL ...');
如果我們要查詢title和body中包含 database的記錄,sql語句如下:

> select * from articles where title like '%database%' or body like '%database%';
這種情況無法通過建立普通索引來提高查詢效率。
只能建立全文索引:

> alter table articles add fulltext index `fi_tb` (`title`,`body`);
使用全文索引需要使用特殊的匹配語法:

> select * from articles where match(title,body) against('database');
match() against() 返回的關鍵字的匹配度,(關鍵字與記錄的關聯程式)

> select * from articles where match(title,body) against('in');
上述語句沒有返回結果。
原因?全文索引索引的關鍵字,不是整個欄位資料,而是從資料中提取的關鍵詞。
而停止詞是不被索引的。

(*mysql的全文索引不支援中文)

3、索引的資料結構
hash
b-tree
兩種資料結構,指的是mysql儲存索引所採用的資料結構。其中使用者所維護的所有索引結構b-tree結構。

4、聚簇索引
在innodb儲存引擎上,主索引是與資料記錄儲存在一起的(聚簇在一起)。

帶來的問題?
innodb的其他索引,非主鍵索引(二級索引),
關鍵字對應的不再是記錄的地址,而是記錄的主鍵。
所以,查詢需要二次檢索,先檢索到ID,在檢索記錄。

5、查詢快取query_cache
將select的結果,儲存起來供二次使用。
開啟查詢快取:

> show variables like 'query_cache%';
mysql優化概述3 - 懷素真 - 因上努力 果上隨緣
> set global query_cache_type = 1;

> set global query_cache_size = 1024*1024*32;
注意事項:
(1)、查詢快取的存在判斷是嚴重依賴於select語句本身,嚴格保證sql一致(包括大小寫)。
(2)、如果查詢時包括動態資料則不能快取。
(3)、一旦開啟了查詢快取,mysql會將所有可以被快取的select語句都快取,如果不想被快取,
可以使用SQL_NO_CACHE來指定不快取。

> select SQL_NO_CACHE * from student where id = 5;

 

相關文章