我有一个 MyISAM 格式的大约 300M 行的表,我想转换为 Innodb
我最初的目标是通过将表架构更改为具有更简单的索引来减少使用。我转储了所有表,删除了它,用更少的索引重新创建它,现在正在重新导入。但是,我忘记指定它应该是innodb而不是myisam。
我可以做标准的 ALTER TABLE ... ENGINE=INNODB 吗?这么大的桌子有什么特别我应该注意的吗?
数据导入操作大约需要 12 个小时——我不想再这样做了。因此,为什么我只想转换它。
KPW*_*INC 14
以下摘录来自“高性能 MySQL,第二版”一书。
这是一本很棒的书,我会推荐给任何人。
简短的回答是:
根据您的桌子大小和条件,无论您选择哪种方法,我认为您都可能要等待很长时间。
表转换
有多种方法可以将表从一种存储引擎转换为另一种存储引擎,每种方法都有优点和缺点。
更改表
mysql> ALTER TABLE mytable ENGINE = Falcon;
Run Code Online (Sandbox Code Playgroud)
这种语法适用于所有存储引擎,但有一个问题:它可能需要很多时间。MySQL 会将旧表逐行复制到新表中。在此期间,您可能会使用服务器的所有磁盘 I/O 容量,并且在转换运行时原始表将被读锁定。
转储和导入
为了更好地控制转换过程,您可以选择首先使用 mysqldump 实用程序将表转储到文本文件。转储表后,您可以简单地编辑转储文件来调整它包含的 CREATE TABLE 语句。一定要更改表名及其类型,因为即使它们的类型不同,在同一个数据库中也不能有两个同名的表——而且 mysqldump 默认在 CREATE TABLE 之前编写 DROP TABLE 命令,所以如果你不小心,你可能会丢失你的数据!
创建和选择
第三种转换技术是第一种机制的速度和第二种机制的安全性之间的折衷。而不是转储整个表或一次全部转换,创建新表并使用 MySQL 的 INSERT ... SELECT 语法来填充它,如下所示:
mysql> CREATE TABLE innodb_table LIKE myisam_table;
mysql> ALTER TABLE innodb_table ENGINE=InnoDB;
mysql> INSERT INTO innodb_table SELECT * FROM myisam_table;
Run Code Online (Sandbox Code Playgroud)
如果您没有太多数据,这很有效,但如果您有,则增量填充表通常更有效,在每个块之间提交事务,因此撤消日志不会变得很大。假设 id 是主键,重复运行此查询(每次使用较大的 x 和 y 值),直到将所有数据复制到新表:
mysql> START TRANSACTION;
mysql> INSERT INTO innodb_table SELECT * FROM myisam_table
-> WHERE id BETWEEN x AND y;
mysql> COMMIT;
Run Code Online (Sandbox Code Playgroud)
这样做之后,您将留下原始表(完成后可以删除它)和新表(现在已完全填充)。如果需要,请小心锁定原始表,以防止获得不一致的数据副本!
归档时间: |
|
查看次数: |
7281 次 |
最近记录: |