您的位置:首页 > 数据库 > SQL

table_open_cache参数对mysql性能的影响

2015-09-09 10:54 726 查看
转自:http://blog.itpub.net/15480802/viewspace-755274/

Table_open_cache:表描述符缓存大小,可减少文件打开/关闭次数;

为了避免线程相互干扰,每个访问表的线程各自维护一个文件描述符,多耗了内存但是提高了性能,即一个sql若调用了2次表,也需要分配2个文件描述符;
对于MyISAM表,第一次打开时需要两个描述符,其中一个为索引文件(可被后续线程共享);
假定系统有200个并发连接,则需将此参数设置为200*N(N为每个连接所需的文件描述符数目);
倘若cache已满且没有可清理的对象,则会临时调大该值,类似于oracle的pga设置;
可通过监控系统状态变量opened_tables查看此cache的繁忙程度,如果opened_tables不断飙升且系统不运行flush tables,则考虑加大table_open_cache值;
当无法为新连接分配足够的描述符时,会遭遇ERROR '...' not found (errno: 23)或者 Can't open file: ... (errno: 24),此时可考虑减小table_open_cache或max_connections
也可以通过open_files_limit调大mysqld可打开的文件数目,但依旧受shell limit所限
凡事无绝对,过大的table_open_cache也有可能会造成拖累,参照如下例子:
版本为5.0.67,该系统有81个数据库且全为MyISAM和MyISAM merge表,在查询information_schema下的tables表时速度奇慢
mysql> SELECT COUNT(*) FROM tables;
+----------+
| COUNT(*) |
+----------+
| 23687 |
+----------+
1 row in set (4 min 37.46 sec
另外涉及连接tables和columns两表的sql经常遭遇 errcode:24,相关参数为open_files_limit=65535和table_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文件数量
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: