InnoDB存储引擎
InnoDB的数据存储在表空间中,采用 MVCC(多版本并发控制)来支持高并发,并且实现了四个标准隔离级别。默认级别是 REPEATABLE READ,并且通过(next-key Lock)策略阻止幻读的出现。next-key 锁是的InnoDB 不仅仅锁定查询涉及的行,还会对索引中间的间隙进行锁定,以防止幻影行的插入。
InnoDB 表是基于聚簇索引建立的,聚簇索引对主键查询有很高的性能。不过它的二级索引(scondary index ,非主键索引)中必须包含主键列,所以如果主键列很大的话,其他所有的索引都会很大。因此若表上的索引较多的话,主键应当尽可能的小。InnoDB的存储格式是平台独立的。
InnoDB内部做了很多优化,包括从磁盘读取数据的时候采用的可预测性预读,能够自动在内存中创建hash索引以加速读操作的自适应性哈希索引(adaptive hash index),以及能够加速插入操作的插入缓冲区(insert buffer)等。
作为事物型的存储引擎,InnoDB 通过一些机制支持真正的热备份,MySQL的其他引擎不支持。
MyISAM存储引擎
MyISAM存储引擎在MySQL 5.1之前的版本是默认的存储引擎。MyISAM提供了大量的特性,包括全文索引、压缩、空间函数等,但是它不支持事物和行级锁,而且在崩溃后无法恢复。对于只读的数据,或者表比较小、可以忍受修复操作,依然可以继续使用MyISAM,但默认推荐InnoDB。
MyISAM 会将表存储在两个文件中:数据文件和索引文件,分别以 .MYD
和.MYI
为扩展名。MyISAM 表可以包含动态或静态(长度固定)的行。MySQL 会根据表的定义来决定采用何种格式。MyISAM 表可以存储的行记录数,一般受限于可用的磁盘空间,或者操作系统中单个文件的最大尺寸。
特性
加锁与并发
MyISAM 对整张表加锁,而不是针对行。读取时会对需要读到的表加共享锁,写入时对表加排它锁。但是在表有读取查询的同时,也可以往表中插入新的记录(并发插入)。
修复
对于MyISAM 表,MySQL 可以手工或者自动执行检查和修复操作,这里说的修复和事物修复以及 崩溃恢复是不同的概念。执行表的修复可能导致一些数据丢失,而且修复操作时非常缓慢的。可以通过 CHECK TABLE mytable
检查表的错误,如果有错误可以通过执行REPAIR TABLE mytable
进行修复。另外,如果 MySQL服务器已经关闭,也可以通过 myisamchk 命令行工具进行检查和修复操作。
索引特性
对于 MyISAM 表,即使是 BLOB 和 TEXT 等长字段,也可以基于其前500个字符创建索引。MyISAM 也支持全文索引。
MyISAM压缩表
如果表在创建并导入数据以后,不会再进行修改操作,那么这样的表或许适合采用 MyISAM 压缩表。
可以使用 myisampack
对 MyISAM 表进行压缩。压缩表是不能进行修改的。压缩表可以极大的减少磁盘空间占用,因此可以减少磁盘I/0,从而提升查询性能。压缩表也支持索引,但索引也是只读的。压缩时表中的记录是独立压缩的,所以读取单行的时候不需要解压整个表(甚至也不解压行所在的整个页面)。
主键索引:
MyISAM引擎使用B+Tree作为索引结构,叶节点的data域存放的是数据记录的地址。下图是MyISAM主键索引的原理图:
辅助索引(Secondary key)
在MyISAM中,主索引和辅助索引(Secondary key)在结构上没有任何区别,只是主索引要求key是唯一的,而辅助索引的key可以重复。
同样也是一颗B+Tree,data域保存数据记录的地址。因此,MyISAM中索引检索的算法为首先按照B+Tree搜索算法搜索索引,如果指定的Key存在,则取出其data域的值,然后以data域的值为地址,读取相应数据记录。
MyISAM的索引方式也叫做“非聚集”的,之所以这么称呼是为了与InnoDB的聚集索引区分。
其他存储引擎
Archive引擎
Archive 存储引擎只支持 INSERT 和SELECT 操作,在MySQL 5.1 之前也不支持索引。是一个针对高速插入和压缩做了优化的简单引擎。
Blackhole引擎
Blackhole 引擎没有实现任何的存储机制,它会丢弃所有插入的数据,不做任何保存。但是服务器会记录Blasckhole 表的日志,所以可以用于复制数据到数据库,或者只是简单地记录到日志。这种特殊的存储引擎可以在一些特殊的复制架构和日志审核时发挥作用。
CSV引擎
CSV引擎可以将普通的CSV文件作为MySQL 的表来处理,但这种表不支持索引。CSV引擎可以作为一种数据交换机制。
Federated 引擎
Federated引擎是访问其他MySQL 服务器的一个代理,默认是禁用的。
Memory引擎
如果需要快速的访问数据,并且这些数据不会被修改,重启以后丢失也没有关系,那么使用Memory表是非常有用的。Memory表比MyIASM 表要快一个数量级,因为所有的数据都保存在内存中,不需要进行磁盘I/O。Memory 表的结构在重启以后还会保留,但数据会丢失。
Memory 表支持hash 索引,因此查找的速度非常快。因为是表级锁,因此并发写入的性能较低。不支持BLOB和TEXT 类型的列,并且每行的长度是固定的,即使指定了VARCHAR列,实际存储时也会转换成CHAR。
如果MySQL 在执行查询的过程中需要使用临时表来保存中间结果,内部使用的临时表就是Memorty 表。如果中间结果太大超出了Memory表的限制,或者含有BLOB或TEXT 字段,则临时表会转换成MyISAM 表。
NDB 集群引擎
MySQL 服务器、NDB集群存储引擎,以及分布式的、share-nothing的、容灾的、高可用的NDB 数据库的组合,被称为MySQL 集群。(MySQL Cluster)