MySQL 5.7中MyISAM和InnoDB存储引擎有哪些当前的区别?

4

我在stackoverflow上看到很多关于MyISAM vs InnoDB的问题和答案。

但是,所有的问题和答案都太老了,与当前稳定版本的MySQL 5.7.x无关。

到目前为止,在MyISAMInnoDB两个存储引擎中一定进行了很多开发。

所以,我需要目前版本5.7.x中这些差异的信息。

请不要标记我的问题重复,并请有人解释当前这些存储引擎的差异以及它们自过去以来的差异。

此外,请解释在什么情况下应该选择哪个存储引擎来创建表。

一个架构中的不同表可以使用不同的存储引擎吗?也就是说,一些表��拥有InnoDB,而另一些表将拥有MyISAM

如果可以,那么在具有MyISAMInnoDB的表之间如何执行JOIN查询?

是否真的有MySQL将来会删除MyISAM存储引擎的计划?


2
你为什么不去阅读文档,而是在这里提问呢? - wallyk
4
也许他们不是以处理数据库为生的人?因此,数据量可能会让人感到困惑。所以出于无知提问,并希望得到友好的回答并不难以置信。 - Maelish
2个回答

15
你的假设MyISAM一直在接受新的开发是不正确的。MyISAM没有接受任何重大的新开发。MySQL明显正在向淘汰MyISAM的方向发展,并且不鼓励使用MyISAM。
Oracle公司尚未宣布任何具体的日期或版本,以便他们将删除MyISAM。我的猜测是MyISAM永远不会被完全删除,因为有太多的网站无法升级,而不进行昂贵的测试,以确保他们特定的应用程序转换为InnoDB时不会遇到任何回归问题。
但是你可能会注意到,在MySQL 5.7手册中,关于MyISAM的章节已经降级为替代存储引擎,这应该是一个提示,它正在接收较低的优先级。
在MySQL 5.7中,MyISAM仍然用于某些系统表,例如mysql.usermysql.db等。但是在5.6和5.7中引入的新系统表都是InnoDB。在MySQL 8.0中,所有系统表都是InnoDB。
MyISAM仍然不支持ACID的任何属性。没有事务,没有一致性特性,也没有持久的写入。请参阅我的答案MyISAM versus InnoDB

就价值而言,MyISAM仍然不支持外键。但是即使使用InnoDB,我很少看到真正的生产站使用外键。

MyISAM仅支持表级锁定(除了一些插入附加到表末尾的情况,如手册中所述)。

MySQL 5.7在MyISAM和InnoDB中都支持全文索引空间索引。这些功能不再是继续使用MyISAM的原因。

mysqldump这样的逻辑备份工具和Percona XtraBackup这样的物理备份工具无法在不获取全局锁的情况下备份MyISAM表。

你问是否可以在同一个模式中创建不同存储引擎的各种表。是的,你可以,这与许多版本的MySQL相同。

你问是否可以连接不同存储引擎的表(顺便说一句,表不需要在同一个模式中才能连接)。是的,你可以连接这些表,MySQL会处理所有细节。这与许多版本的MySQL相同。

但是,当您在事务中更新MyISAM表和InnoDB表,然后回滚时,可能会出现一些奇怪的情况。 InnoDB表中的更改将被回滚,但是MyISAM表中的更改不会被回滚,因此如果您不小心,数据完整性可能会被破坏。这也与许多版本的MySQL相同。
MyISAM比InnoDB更具优势的情况很少,而且越来越少了。
  • Some table-scan queries and bulk inserts are faster in MyISAM. InnoDB is better at indexed searches.

  • MyISAM may use less storage space than the equivalent data stored in an uncompressed InnoDB table. You can further compact MyISAM tables with myisampack, but this makes the MyISAM table read-only.

    There are other options these days for compact storage of data in transactional storage engines, for example InnoDB table compression, or MyRocks.

  • SELECT COUNT(*) FROM MyTable queries (with no WHERE clause) are very fast in MyISAM, because the accurate count of rows is persisted in the MyISAM metadata. InnoDB (or other MVCC implementations) doesn't keep this count persisted, because every transaction viewing the table might "see" a different row count. Only a storage engine that has table-level locking and no transaction isolation like MyISAM, can optimize this case.

  • Auto-increment that numbers independently for each distinct value in another key column. Again, this requires table-level locking, so it's not supported in InnoDB.

    CREATE TABLE MyTable (
      group_id INT NOT NULL,
      seq_id INT NOT NULL AUTO_INCREMENT,
      PRIMARY KEY (group_id, seq_id)
    ) ENGINE=MyISAM;
    
  • It's still easy to move a MyISAM table from server to server, because the .MYD and .MYI files are self-contained. You can kind of do something similar with InnoDB tables, but you have to use the intricate feature of transportable tablespaces. But this easy-to-move-tables quality of MyISAM no longer works in MySQL 8.0, because of their new data dictionary feature.

  • Under certain load, MyISAM might be a better choice for internal_tmp_disk_storage_engine, which defaults to InnoDB in MySQL 5.7. If you run lots of queries that create temp tables on disk (in-memory temp tables won't benefit), it can put a strain on the InnoDB engine. But you'd have to have a high query rate for this to matter, and if your queries create so many temp tables on disk, you should try to optimize the queries differently.

  • MyISAM allows you to set multiple key caches, and define caches for specific tables. But the MyISAM key caches are only for index structures, not for data.

参考文献:

https://www.percona.com/blog/2016/10/11/mysql-8-0-end-myisam/

https://www.percona.com/blog/2017/12/04/internal-temporary-tables-mysql-5-7/

http://jfg-mysql.blogspot.com/2017/08/why-we-still-need-myisam.html


2

我在一次工作测验中遇到了这个问题,并且回答正确:(指的是新版本)

MyISAM和InnoDB是两种不同的存储引擎,它们以不同的方式处理CRUD操作。

  • 锁定:访问MyISAM存储引擎中的一行时,其他会话将锁定整个表,直到更改被提交,而InnoDB仅锁定特定选定的行。锁定将延迟其他试图与相同表或行交互的会话,以防止例如表中的错误数据操作。

  • 事务:InnoDB支持事务,而MyISAM不支持。事务是由2个或多个命令(如SELECT、INSERT、UPDATE和DELETE)组成的集合,作为单个操作执行,直到完成。

    1. 原子操作:在InnoDB中设置事务并且操作未完成时,它将终止所有更改并恢复数据库(全部或无),因此例如,如果在事务的中间有代码/数据类型不匹配等任何可能中断命令束以完成其操作的情况-所有更改都不会应用,感谢事务的原子性。另一方面,当使用MyISAM存储引擎时,如果一组命令“中断”(出于任何原因),操作将立即停止,并且所有受影响的表/行/数据将保持受影响状态,这可能会导致数据库中的损坏数据(...和头疼)。

    2. B. 在MyISAM上运行操作是即时设置的,而InnoDB允许您使用“ROLLBACK”来丢弃任何更改,这在运行事务时非常方便。

    3. 事务日志:在没有事务日志的情况下创建事务,您可以对DB中的表进行任何更改,如果表具有聚集索引(例如),则数据必须搜索要插入的位置,然后才能应用更改。如果DB和事务之间存在事务日志,则更改将首先发送到事务日志,并在将更改发送到DB之前在表中设置其顺序-这将减少时间消耗。 DB保存了所有已进行的事务的日志,这可以帮助选择恢复以前进行的任何事务并恢复所有更改。当设置为“简单”恢复模型时-事务从事务日志中删除,并且无法恢复数据(通常在DEV环境中使用)。当设置为“完全”恢复模型时,保存并列出所有事务,以备恢复-这通常在生产环境中使用,可能会导致问题,例如性能问题-因此备份它们并从服务器中删除可能是一个解决方案。当设置为“批量记录”恢复模型时,仅为特定的“重要”更改和命令(导入、导出、插入选择、选择-进入、重新组织/重建索引)保存事务日志,可能会防止性能问题。

  • 外键:MyISAM不使用外键,而InnoDB使用。当表列具有设置为指向其他表列的外键时,指向表上发生任何更新/删除时,它将知道必须应用对其指向的另一个表的更改。这在两个表之间创建了某种链接并使数据保持同步。设置具有FK的表可能需要更多的工作,这可能被认为是一个缺点(?)。

  • FULLTEXT索引:InnoDB在其先前版本中不支持FULLTEXT索引-MyISAM支持它。切换到MyISAM不是最好的解决方案,因此只需将MySQL更新到支持FULLTEXT索引的版本即可。 FULLTEXT索引可以接受标题、注释等文本,并

    总的来说,InnoDB在数据处理、有效性和恢复方面通常更加可靠。对于新版本,InnoDB将支持FULLTEXT索引,主要用于搜索。如果使用无法更新MySQL的旧版本,则使用MyISAM会很好。请保留HTML标签。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接