如何在mysql中提高重插入的性能?

时间:2013-03-02 00:55:07

标签: mysql innodb myisam

我正在研究提高插入的mysql性能的方法。

关于这个场景,在忙碌的一天中,每3秒约有3000行用于大表,另外100用于中等表,约30用于小表。这必须持续24小时,然后我选择的重要部分只有30.000-40.000行,然后我正在冲洗所有3个表。

所以,我正在使用mysql 5.5.29。所有表都使用innodb,索引和主键都很少。

关于这个问题,我看到了关于为这些插入使用内存引擎表然后将它们移动到主表的注释:

“使用LOCK TABLE .. WRITE可以加快插入速度,但是当处理和加载行时,你将锁定任何读卡器。主键上的选择(应该接近0秒)最多需要0.2我的加载程序忙于加载1000行批次时的秒数。

一个非常好的解决方法是将新行放入临时表,然后立即刷新该表,然后在单个tansaction中。这使插入非常快,因为所有检查和转换都已在临时表中完成。

CREATE TEMPORARY TABLE ..._temp (....) ENGINE=MEMORY;

-- Loop from here --
DELETE FROM .._temp;
INSERT INTO .._temp ... VALUES (...);
INSERT INTO .._temp ... VALUES (...);

LOCK TABLE ... WRITE, ..._temp READ;
INSERT INTO ... SELECT * FROM ..._temp;
UNLOCK TABLES;
-- Repeat until done --

DROP TABLE ..._temp;

我在系统中看到的是,INSERT的速度与锁定表时的速度大致相同,但是当加载程序运行时,客户端根本没有注意到任何性能损失。“

Source

在这种情况下使用内存引擎是否有意义? 如果需要访问行,我应该使用innodb来获取表锁吗?或者我更喜欢myisam的速度?

1 个答案:

答案 0 :(得分:3)

如果您需要每天擦拭您的桌子,但需要先从中获取数据。最好的办法是快速将现有的全表替换为新的空表,然后在完整的表上执行所需的任何数据操作。这是你如何做到的。

首先创建一个表,就像您尝试操作的表一样:

CREATE TABLE big_table_temp LIKE big_table;

现在您有一个与大表具有相同模式的空表。

然后重命名表格以将它们交换出来:

RENAME TABLE big_table TO big_table_archive, big_table_temp TO big_table;

这样做的好处是这个操作基本上是即时的,因为MySQL只是重命名磁盘上的二进制数据库文件。确保在一个查询中同时具有重命名操作,因为您希望操作成功或失败。

然后,您可以根据需要对big_table_archive进行操作,从中提取数据,而无需担心阻止big_table上的实时查询。