MySQL碎片整理方法

jopen 9年前
 

对于一个表如果经常插入数据和删除数据,则会产生很多不连续的碎片,这样久而久之,这个表就会占用很大空间,但实际上表里面的记录数却很少,这样不但会浪费空间,并且查询速度也更慢,因此为了解决这个问题,可以有心下解决方案

1、myisam存储引擎清理碎片方法

OPTIMIZE TABLE  table_name

2、innodb存储引擎清理碎片方法

ALTER TABLE tablename ENGINE=InnoDB

3、查看表碎片的方法

mysql> select ROW_FORMAT,TABLE_ROWS,DATA_LENGTH,INDEX_LENGTH,MAX_DATA_LENGTH,DATA_FREE,ENGINE from TABLES where TABLE_SCHEMA='test_db' and TABLE_NAME='test_table' limit 1;

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

| ROW_FORMAT | TABLE_ROWS | DATA_LENGTH | INDEX_LENGTH | MAX_DATA_LENGTH | DATA_FREE  | ENGINE |

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

| Dynamic    |    2250014 |  4042158980 |   2338186240 | 281474976710655 | 3901819476 | MyISAM |

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

1 row in set (0.00 sec)

从上面的DATA_FREE字段可以看出碎片空间很大

Engine不同,OPTIMIZE 的操作也不一样的,MyISAM 因为索引和数据是分开的,所以 OPTIMIZE 可以整理数据文件,并重排索引.

OPTIMIZE 操作会暂时锁住表,而且数据量越大,耗费的时间也越长,它毕竟不是简单查询操作.所以把 Optimize 命令放在程序中是不妥当的,不管设置的命中率多低,当访问量增大的时候,整体命中率也会上升,这样肯定会对程序的运行效率造成很大影响.比较好的方式就是做个shell,定期检查mysql中 `information_schema`.`TABLES`字段,查看 DATA_FREE 字段,大于0话,就表示有碎片