国内最全IT社区平台 联系我们 | 收藏本站
华晨云阿里云优惠2
您当前位置:首页 > 数据库 > 数据库应用 > 谈谈MySQL的存储引擎

谈谈MySQL的存储引擎

来源:程序员人生   发布时间:2016-09-28 09:56:17 阅读次数:2991次

微信扫1扫关注我的公众号或搜索添加“MySQL技术的学习分享”,可以更快速更实时地获得我的最新文章。


MySQL的存储引擎是MySQL体系架构中的重要组成部份,也是MySQL体系结构的核心,插件式的存储引擎更是它区分于其它数据库的重要特点。它处于MySQL体系架构中Server端底层,是底层物理结构的实现,用于将数据以各种不同的技术方式存储到文件或内存中,不同的存储引擎具有不同的存储机制、索引技能和锁定水平。常见的MySQL存储引擎有InnoDBMyISAMMemoryArchive等等,它们具有各自的特点,我们可以根据不同的具体利用来建立对应的存储引擎表。

在谈不同的存储引擎之前,我们需要先理解几个基本概念:


(1)  事务

   事务是1组原子性的SQL语句或说是1个独立的工作单元,如果数据库引擎能够成功对数据库利用这组SQL语句,那末就履行,如果其中有任何1条语句由于崩溃或其它缘由没法履行,那末所有的语句都不会履行。也就是说,事务内的语句,要末全部履行成功,要末全部履行失败。

举个银行利用的典型例子:

   假定银行的数据库有两张表:支票表和储蓄表,现在某个客户A要从其支票账户转移2000元到其储蓄账户,那末最少需求3个步骤:

a.检查A的支票账户余额高于2000元;

b.从A的支票账户余额中减去2000元;

c.在A的储蓄账户余额中增加2000元。

    这3个步骤必须要打包在1个事务中,任何1个步骤失败,则必须要回滚所有的步骤,否则A作为银行的客户便可能要莫名损失2000元,就出问题了。这就是1个典型的事务,这个事务是不可分割的最小工作单元,全部事务中的所有操作要末全部提交成功,要末全部失败回滚,不可能只履行其中1部份,这也是事务的原子性特点。


(2)  读锁和写锁

   不管什么时候,只要有多个SQL需要同1时刻修改数据,都会产生并发控制的问题。

   假定1个公共邮箱,用户A正在读取邮箱,同时,用户B正在删除邮箱中的某个邮件,会产生甚么结果呢?客户A可能读取时会报错退出,也可能会读取到不1致的邮箱数据。如果把邮箱当作数据库中的1张表,可见其存在一样的问题。

    解决这类经典问题的方法就是并发控制,即在处理并发读或写时,可以通过实现1个由两种类型的锁组成的锁系统来解决问题。这两种锁就是同享锁和排他锁,也叫读锁和写锁。

     读锁是同享的,即相互不阻塞的,多个客户在同1时刻可以读取同1资源,互不干扰。写锁是排他的,即1个写锁会阻塞其它的写锁和读锁,只有这样,才能确保给定时间内,只有1个用户能履行写入,避免其它用户读取正在写入的同1资源。写锁优先级高于读锁。


(3)  行锁和表锁

    实际数据库系统中每时每刻都在产生锁定,锁也是有粒度的,提高同享资源并发行的方式就是让锁更有选择性,尽可能只锁定需要修改的部份数据,而不是所有的资源,因此要进行精确的锁定。但是由于加锁也需要消耗资源,包括取得锁、检查锁是不是消除、释放锁等,都会增加系统的开消。所谓的锁策略就是要在锁的开消和数据的安全性之间寻求平衡,这类平衡也会影响性能。  

    每种MySQL存储引擎都有自己的锁策略和锁粒度,最经常使用的两种重要的锁策略分别是表锁和行锁。

    表锁是开消最小的策略,会锁定整张表,用户对表做写操作时,要先取得写锁,这会阻塞其它用户对该表的所有读写操作。没有写锁时,其它读取的用户才能取得读锁,读锁之间是不相互阻塞的。行锁可以最大成都支持并发处理,但也带来了最大的锁开消,它只对指定的记录加锁,其它进程还是可以对同1表中的其它记录进行操作。表级锁速度快,但冲突多,行级锁冲突少,但速度慢。      

 

理解了上面几个概念,我们就能够很好地分辨不同存储引擎之间的区分了。


  1. InnoDB存储引擎

MySQL存储引擎可以分为官方存储引擎和第3方存储引擎,InnoDB就是强大的第3方存储引擎,具有较好的性能和自动崩溃恢复特性,目前利用极其广泛,是当前MySQL存储引擎中的主流,它在事务型存储和非事务型存储中都很流行。

InnoDB存储引擎支持事务、支持行锁、支持非锁定读、支持外键。

如非特别缘由,利用建表时都可以首选斟酌使用InnoDBInnoDB也是1个非常好的值得花时间去深入学习的存储引擎,后续计划专题研究这个存储引擎,这里就暂不赘述其详细内容了。


2. MyISAM存储引擎

MyISAM存储引擎是MySQL官方提供的存储引擎,它在InnoDB出现并完善之前是MySQL存储引擎的主流,但目前逐步被淘汰主要由于其不支持事务,这也许源于MySQL的开发者认为不是所有的利用都需要事务,所以便存在了这类不支持事务的存储引擎。

MyISAM不支持事务,不支持行级锁,支持表锁,支持全文索引,最大的缺点是崩溃后没法安全恢复。

MyISAM因设计简单,数据以紧密格式存储,所以某些场景下性能很好,但是它的表锁又带来了性能问题,如果你发现所有的查询都长时间处于“Locked”状态,表锁就是罪魁罪魁了。

因此,对只读数据,或表比较小,可以忍耐修复操作的可以仍然使

MyISAM,对不需要事务的利用,选择MyISAM存储引擎,也许可以取得更高的性能,MySQL自带的默许的information_schema库中就存在使用MyISAM存储引擎的表。

| TRIGGERS | CREATETEMPORARY TABLE `TRIGGERS` (

  `TRIGGER_CATALOG` varchar(512) NOT NULLDEFAULT '',

  `TRIGGER_SCHEMA` varchar(64) NOT NULL DEFAULT'',

  `TRIGGER_NAME` varchar(64) NOT NULL DEFAULT'',

  `EVENT_MANIPULATION` varchar(6) NOT NULLDEFAULT '',

  `EVENT_OBJECT_CATALOG` varchar(512) NOT NULLDEFAULT '',

  `EVENT_OBJECT_SCHEMA` varchar(64) NOT NULLDEFAULT '',

  `EVENT_OBJECT_TABLE` varchar(64) NOT NULLDEFAULT '',

  `ACTION_ORDER` bigint(4) NOT NULL DEFAULT'0',

  `ACTION_CONDITION` longtext,

  `ACTION_STATEMENT` longtext NOT NULL,

  `ACTION_ORIENTATION` varchar(9) NOT NULLDEFAULT '',

  `ACTION_TIMING` varchar(6) NOT NULL DEFAULT'',

  `ACTION_REFERENCE_OLD_TABLE` varchar(64)DEFAULT NULL,

  `ACTION_REFERENCE_NEW_TABLE` varchar(64)DEFAULT NULL,

  `ACTION_REFERENCE_OLD_ROW` varchar(3) NOTNULL DEFAULT '',

  `ACTION_REFERENCE_NEW_ROW` varchar(3) NOTNULL DEFAULT '',

  `CREATED` datetime DEFAULT NULL,

  `SQL_MODE` varchar(8192) NOT NULL DEFAULT '',

  `DEFINER` varchar(77) NOT NULL DEFAULT '',

  `CHARACTER_SET_CLIENT` varchar(32) NOT NULLDEFAULT '',

  `COLLATION_CONNECTION` varchar(32) NOT NULLDEFAULT '',

  `DATABASE_COLLATION` varchar(32) NOT NULLDEFAULT ''

)ENGINE=MyISAM DEFAULT CHARSET=utf8 |


3. Memory存储引擎

Memory存储引擎将表中数据放在内存中,因此速度非常快,但因其支持表锁,所以并发性能较差,最糟的是这个存储引擎在数据库重启或崩溃以后表中的数据将全部丢失,它只适用于存储临时数据的临时表,MySQL中1般使用这个存储引擎来寄存查询的中间结果集,如MySQL自带的默许的information_schema库中就存在较多使用Memory存储引擎的表。

|TABLES | CREATE TEMPORARY TABLE `TABLES` (

  `TABLE_CATALOG` varchar(512) NOT NULL DEFAULT'',

  `TABLE_SCHEMA` varchar(64) NOT NULL DEFAULT'',

  `TABLE_NAME` varchar(64) NOT NULL DEFAULT '',

  `TABLE_TYPE` varchar(64) NOT NULL DEFAULT '',

  `ENGINE` varchar(64) DEFAULT NULL,

  `VERSION` bigint(21) unsigned DEFAULT NULL,

  `ROW_FORMAT` varchar(10) DEFAULT NULL,

  `TABLE_ROWS` bigint(21) unsigned DEFAULTNULL,

  `AVG_ROW_LENGTH` bigint(21) unsigned DEFAULTNULL,

  `DATA_LENGTH` bigint(21) unsigned DEFAULTNULL,

  `MAX_DATA_LENGTH` bigint(21) unsigned DEFAULTNULL,

  `INDEX_LENGTH` bigint(21) unsigned DEFAULTNULL,

  `DATA_FREE` bigint(21) unsigned DEFAULT NULL,

  `AUTO_INCREMENT` bigint(21) unsigned DEFAULTNULL,

  `CREATE_TIME` datetime DEFAULT NULL,

  `UPDATE_TIME` datetime DEFAULT NULL,

  `CHECK_TIME` datetime DEFAULT NULL,

  `TABLE_COLLATION` varchar(32) DEFAULT NULL,

  `CHECKSUM` bigint(21) unsigned DEFAULT NULL,

  `CREATE_OPTIONS` varchar(255) DEFAULT NULL,

  `TABLE_COMMENT` varchar(2048) NOT NULLDEFAULT ''

) ENGINE=MEMORY DEFAULT CHARSET=utf8| 


4. Archive存储引擎

   Archive存储引擎置只支持INSERTSELECT操作,支持行锁,但本身其实不是事务安全的存储引擎,其最大的优点是其具有较好的紧缩比,紧缩比1般可到达1:10,可以将一样的数据以更小的磁盘空间占用来存储。

   Archive存储引擎非常合适存储归档数据,如历史数据、日志信息数据等等,这类数据常常数据量非常大,并且基本只有INSERTSELECT操作,使用这个存储引擎可以非常节俭磁盘空间。

  以某个库里的有2.5亿条记录的历史表为例:

mysql> select TABLE_ROWSfrom TABLES where TABLE_NAME='history';

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

| TABLE_ROWS |

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

|  251755162 |

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

1 row in set (0.01 sec)

       本来其默许为InnoDB存储引擎时,该表大小为12G

生活不易,码农辛苦
如果您觉得本网站对您的学习有所帮助,可以手机扫描二维码进行捐赠
程序员人生
------分隔线----------------------------
分享到:
------分隔线----------------------------
关闭
程序员人生