1. 程式人生 > >MYSQL-查詢緩存

MYSQL-查詢緩存

緩存 單個 flush 效應 清理 sql語句 最大 疑問 用戶

查詢的執行路徑

技術分享圖片

過程:

數據默認是放在磁盤上的文件,如果我們每次查詢都要去磁盤上查找,效率是非常低下的。但是我們把查詢過的數據放在緩存中,讓內存代替磁盤來進行查詢,那麽效率是非常高的。

1、客戶端通過與服務器之間的通信協議,微軟的SQLserver有SQLserver的協議,Oracle有Oracle的協議,MySQL有MySQL的協議。
2、通過協議連接之後,客戶端向服務器發送一個select的查詢,如果服務器的緩存是打開的,那麽服務器先去緩存空間中查找,如果有,則直接返回給用戶。毫無疑問,這樣的查詢速度是最快的。
3、如果緩存空間沒有,則服務器對客戶發送的指令進行解析,請求的sql語句會生成一個解析樹,通過語法分析,從左到右一個字符一個字符的輸入,根據構詞規則識別單詞,識別sql語句中的關鍵字和非關鍵字,然後進行語法解析,判斷這個SQL語句是否滿足MySQL語法規則,如果語法不對,則會返回報錯信息,提示用戶報錯

如果語法正確,則會檢查解析的語句是否合法,如檢查查詢的表明,字段是否正確,是否有有對應的查詢權限,然後生成新的解析樹。
4、查詢優化器會查詢語句中是否有很好的查詢方法,比如,索引。
5、如果有,則將SQL語句轉換為執行計劃,交給查詢執行引擎,
6、查詢執行引擎根據這個執行計劃來完成整個查詢。
7、調用API接口,連接到數據庫,將要查詢的數據從硬盤中讀取出來
8、將查詢的數據一份返回給客戶端,一份存在緩存空間。
這樣查詢的整個過成就結束了

查詢緩存

查詢緩存( Query Cache )原理

查詢緩存是通過hash來進行查詢的
我們鍵入select指令的時候,系統會對這條語句進行hash運算,得到一串hash值,然後用這串hash值在緩存空間中尋找是否有同樣的hash值,如果有,則返回給用戶,如果沒有,則執行查詢工作

    註意:
    hash運算具有特殊性質:雪崩效應, 當你鍵入同樣的SQL語句的時候,雖然兩次鍵入的SQL語句返回的結果是相同的,但是,一旦多鍵入一個空格,或者其他字符,則生成的hash值則完全不一樣,所以,它不會去緩存空間中尋找。

緩存SELECT操作或預處理查詢的結果集和SQL語句,當有新的SELECT語句或預處理查詢語句請求,先去查詢緩存,判斷是否存在可用的記錄集,判斷標準:與緩存的SQL語句,是否完全一樣,區分大小寫

優缺點

    不需要對SQL語句做任何解析和執行,當然語法解析必須通過在先,直接從Query Cache中獲得查詢結果,提高查詢性能
    查詢緩存的判斷規則,不夠智能,也即提高了查詢緩存的使用門檻,降低其效率;
    查詢緩存的使用,會增加檢查和清理Query Cache中記錄集的開銷 

不會被緩存的數據

1、查詢語句中加了SQL_NO_CACHE參數
2、查詢語句中含有獲得值的函數,包含自定義函數,如:
NOW()、CURDATE()、GET_LOCK()、RAND()、CONVERT_TZ()等
3、對系統數據庫的查詢:mysql、information_schema 查詢語句中使用SESSION級別變量或存儲過程中的局部變量
4、查詢語句中使用了LOCK IN SHARE MODE、FOR UPDATE的語句,查詢語句中類似SELECT …INTO 導出數據的語句
5、對臨時表的查詢操作;存在警告信息的查詢語句;不涉及任何表或視圖的查詢語句;某用戶只有列級別權限的查詢語句
6、事務隔離級別為Serializable時,所有查詢語句都不能緩存

查詢緩存相關的服務器變量

show variables like ‘query_cache%‘; 查詢緩存變量

以下四個及時服務器變量也是服務器選項

query_cache_min_res_unit:

查詢緩存中內存塊的最小分配單位,默認4k,較小值會減少浪費,但會導致更頻繁的內存分配操作,較大值會帶來浪費,會導致碎片過多,內存不足

query_cache_limit:

單個查詢結果能緩存的最大值,默認為1M,對於查詢結果過大而無法緩存的語句,建議使用SQL_NO_CACHE

query_cache_size:

查詢緩存總共可用的內存空間;單位字節,必須是1024的整數倍,最小值40KB,低於此值有警報

query_cache_wlock_invalidate:

如果某表被其它的會話鎖定,是否仍然可以從查詢緩存中返回結果,默認值為OFF,表示可以在表被其它會話鎖定的場景中繼續從緩存返回數據;ON則表示不允許

query_cache_type:

是否開啟緩存功能,取值為ON, OFF, DEMAND

設置緩存變量

將query_cache_size設置為5M

需要註意的是,用SQL語句是只能以字節為單位

需要註意的是,用SQL語句是只能以字節為單位
寫入配置文件可以使用M單位
set global query_cache_size=512000;
vim my.conf
query_cache_size=5M
重啟服務即可

設置query_cache_type為啟動

vim my.conf
query_cache_type=ON
重啟服務即可

查看緩存狀態

查詢緩存相關的狀態變量:SHOW GLOBAL STATUS LIKE ‘Qcache%‘;

Qcache_free_blocks:       處於空閑狀態 Query Cache中內存 Block 數
Qcache_total_blocks:      Query Cache 中總Block ,當Qcache_free_blocks相對此值較大時,可能用內存碎片,執行FLUSH QUERY CACHE清理碎片
Qcache_free_memory:       處於空閑狀態的 Query Cache 內存總量
Qcache_hits:              Query Cache 命中次數
Qcache_inserts:           向 Query Cache 中插入新的 Query Cache 的次數,即沒有命中的次數
Qcache_lowmem_prunes:     記錄因為內存不足而被移除出查詢緩存的查詢數
Qcache_not_cached:        沒有被 Cache 的 SQL 數,包括無法被 Cache 的 SQL 以及由於 query_cache_type 設置的不會被 Cache 的 SQL語句
Qcache_queries_in_cache:  在 Query Cache 中的 SQL 數量

MYSQL-查詢緩存