table_open_cache引數對mysql效能的影響

luckyfriends發表於2016-12-30

Table_open_cache:表描述符快取大小,可減少檔案開啟/關閉次數;

 

為了避免執行緒相互干擾,每個訪問表的執行緒各自維護一個檔案描述符,多耗了記憶體但是提高了效能,即一個sql若呼叫了2次表,也需要分配2個檔案描述符;

對於MyISAM表,第一次開啟時需要兩個描述符,其中一個為索引檔案(可被後續執行緒共享)

假定系統有200個併發連線,則需將此引數設定為200*N(N為每個連線所需的檔案描述符數目)

倘若cache已滿且沒有可清理的物件,則會臨時調大該值,類似於oraclepga設定;

可透過監控系統狀態變數opened_tables檢視此cache的繁忙程度,如果opened_tables不斷飆升且系統不執行flush tables,則考慮加大table_open_cache值;

當無法為新連線分配足夠的描述符時,會遭遇ERROR '...' not found (errno: 23)或者 Can't open file: ... (errno: 24),此時可考慮減小table_open_cachemax_connections

也可以透過open_files_limit調大mysqld可開啟的檔案數目,但依舊受shell limit所限

凡事無絕對,過大的table_open_cache也有可能會造成拖累,參照如下例子:

版本為5.0.67,該系統有81個資料庫且全為MyISAMMyISAM merge表,在查詢information_schema下的tables表時速度奇慢

mysql> SELECT COUNT(*) FROM tables;

+----------+

| COUNT(*) |

+----------+

|    23687 |

+----------+

1 row in set (4 min 37.46 sec

另外涉及連線tablescolumns兩表的sql經常遭遇 errcode24,相關引數為open_files_limit=65535table_cache=32768

呼叫flush tables with read lock關閉系統中所有開啟的表,然後執行上述sql同時監控相應狀態變數

admin@localhost (none)>SHOW STATUS LIKE 'open%';

+---------------+-------+

| Variable_name | Value |

+---------------+-------+

| Open_files    | 22696 |

| Open_streams  | 0     |

| Open_tables   | 8095  |

| Opened_tables | 0     |

+---------------+-------+

4 rows in set (0.00 sec)

再次執行該sql

admin@localhost (none)>SHOW STATUS LIKE 'open%';

+---------------+-------+

| Variable_name | Value |

+---------------+-------+

| Open_files    | 32848 |

| Open_streams  | 0     |

| Open_tables   | 12013 |

| Opened_tables | 0     |

+---------------+-------+

4 rows in set (0.00 sec

table_open_cache降低為5000,相應sql效能反而得到提升;

原因是如果系統同時執行很多複雜sql,則table_open_cache很容易被佔滿,mysql採用線性演算法O(n)找出最近最少使用的表將其清除,當開啟的檔案過多時這一操作會比較耗時;將來的版本會引入hash演算法

 

 

對於innodb表,若為每個表各分配一個資料檔案,則innodb_open_files用來限制可以開啟的.ibd檔案數量

 

來自 “ ITPUB部落格 ” ,連結:http://blog.itpub.net/14710393/viewspace-2131686/,如需轉載,請註明出處,否則將追究法律責任。

相關文章