Mongodb 与 MySQL对比

39次阅读

共计 2661 个字符,预计需要花费 7 分钟才能阅读完成。

在数据库存放的数据中,有一种特殊的键值叫做主键,它用于惟一地标识表中的某一条记录。也就是说,一个表不能有多个主键,并且主键不能为空值。无论是 MongoDB 还是 MySQL,都存在着主键的定义。对于 MongoDB 来说,其主键名叫”_id”,在生成数据的时候,如果用户不主动为其分配一个主键的话,MongoDB 会自动为其生成一个随机分配的值。
在 MySQL 中,主键的指定是在 MySQL 插入数据时指明 PRIMARY KEY 来定义的。当没有指定主键的时候,另一种工具 —— 索引,相当于替代了主键的功能。索引可以为空,也可以有重复,另外有一种不允许重复的索引叫惟一索引。如果既没有指定主键也没有指定索引的话,MySQL 会自动为数据创建一个。
存储速度对比
1. 数据库的平均插入速率:MongoDB 不指定_id 插入 > MySQL 不指定主键插入 > MySQL 指定主键插入 > MongoDB 指定_id 插入。
2. MongoDB 在指定_id 与不指定_id 插入时速度相差很大,而 MySQL 的差别却小很多。

分析:
1. 在指定_id 或主键时,两种数据库在插入时要对索引值进行处理,并查找数据库中是否存在相同的键值,这会减慢插入的速率。
2. 在 MongoDB 中,指定索引插入比不指定慢很多,这是因为,MongoDB 里每一条数据的_id 值都是唯一的。当在不指定_id 插入数据的时候,其_id 是系统自动计算生成的。MongoDB 通过计算机特征值、时间、进程 ID 与随机数来确保生成的_id 是唯一的。而在指定_id 插入时,MongoDB 每插一条数据,都需要检查此_id 可不可用,当数据库中数据条数太多的时候,这一步的查询开销会拖慢整个数据库的插入速度。
3. MongoDB 会充分使用系统内存作为缓存,这是一种非常优秀的特性。我们的测试机的内存有 64G,在插入时,MongoDB 会尽可能地在内存快写不进去数据之后,再将数据持久化保存到硬盘上。这也是在不指定_id 插入的时候,MongoDB 的效率遥遥领先的原因。但在指定_id 插入时,当数据量一大内存装不下时,MongoDB 就需要将磁盘中的信息读取到内存中来查重,这样一来其插入效率反而慢了。
4. MySQL 不愧是一种非常稳定的数据库,无论在指定主键还是在不指定主键插入的情况下,其效率都差不了太多。
插入稳定性分析
插入稳定性是指,随着数据量的增大,每插入一定量数据时的插入速率情况。
在本次测试中,我们把这个指标的规模定在 10w,即显示的数据是在每插入 10w 条数据时,在这段时间内每秒钟能插入多少条数据。
先呈现四张图上来:1. MongoDB 指定_id 插入:
2. MongoDB 不指定_id 插入:3. MySQL 指定 PRIMARY KEY 插入:
4. MySQL 不指定 PRIMARY KEY 插入:

总结:

整体上的插入速度还是和上一回的统计数据类似:MongoDB 不指定_id 插入 > MySQL 不指定主键插入 > MySQL 指定主键插入 > MongoDB 指定_id 插入。
从图中可以看出,在指定主键插入数据的时候,MySQL 与 MongoDB 在不同数据数量级时,每秒插入的数据每隔一段时间就会有一个波动,在图表中显示成为规律的毛刺现象。而在不指定插入数据时,在大多数情况下插入速率都比较平均,但随着数据库中数据的增多,插入的效率在某一时段有瞬间下降,随即又会变稳定。
整体上来看,MongoDB 的速率波动比 MySQL 的严重,方差变化较大。
MongoDB 在指定_id 插入时,当插入的数据变多之后,插入效率有明显地下降。在其他三种的插入测试中,从开始到结束,其插入的速率在大多数的时候都固定在一个标准上。

分析:

毛刺现象是因为,当插入的数据太多的时候,MongoDB 需要将内存中的数据写进硬盘,MySQL 需要重新分表。这些操作每当数据库中的数据达到一定量级后就会自动进行,因此每隔一段时间就会有一个明显的毛刺。
MongoDB 毕竟还是新生事物,其稳定性没有已应用多年的 MySQL 优秀。
MongoDB 在指定_id 插入的时候,其性能的下降还是很厉害的。
在读取的数据规模不大时,MongoDB 的查询速度真是一骑绝尘,甩开 MySQL 好远好远。
在查询的数据量逐渐增多的时候,MySQL 的查询速度是稳步下降的,而 MongoDB 的查询速度却有些起伏。

分析:

如果 MySQL 没有经过查询优化的话,其查询速度就不要跟 MongoDB 比了。MongoDB 可以充分利用系统的内存资源,我们的测试机器内存是 64GB 的,内存越大 MongoDB 的查询速度就越快,毕竟磁盘与内存的 I / O 效率不是一个量级的。
本次实验的查询的数据也是随机生成的,因此所有待查询的数据都存在 MongoDB 的内存缓存中的概率是很小的。在查询时,MongoDB 需要多次将内存中的数据与磁盘进行交互以便查找,因此其查询速率取决于其交互的次数。这样就存在这样一种可能性,尽管待查询的数据数目较多,但这段随机生成的数据被 MongoDB 以较少的次数从磁盘中取出。因此,其查询的平均速度反而更快一些。这样看来,MongoDB 的查询速度波动也处在一个合理的范围内。
MySQL 的稳定性还是毋庸置疑的。

结论

相比较 MySQL,MongoDB 数据库更适合那些读作业较重的任务模型。MongoDB 能充分利用机器的内存资源。如果机器的内存资源丰富的话,MongoDB 的查询效率会快很多。
在带”_id”插入数据的时候,MongoDB 的插入效率其实并不高。如果想充分利用 MongoDB 性能的话,推荐采取不带”_id”的插入方式,然后对相关字段作索引来查询。
MongoDB 适合那些对数据库具体数据格式不明确或者数据库数据格式经常变化的需求模型,而且对开发者十分友好。
MongoDB 官方就自带一个分布式文件系统,可以很方便地部署到服务器机群上。MongoDB 里有一个 Shard 的概念,就是方便为了服务器分片使用的。每增加一台 Shard,MongoDB 的插入性能也会以接近倍数的方式增长,磁盘容量也很可以很方便地扩充。
MongoDB 还自带了对 map-reduce 运算框架的支持,这也很方便进行数据的统计。

MongoDB 的缺陷

事务关系支持薄弱。这也是所有 NoSQL 数据库共同的缺陷,不过 NoSQL 并不是为了事务关系而设计的,具体应用还是很需求。
稳定性有些欠缺,这点从上面的测试便可以看出。
MongoDB 一方面在方便开发者的同时,另一方面对运维人员却提出了相当多的要求。业界并没有成熟的 MongoDB 运维经验,MongoDB 中数据的存放格式也很随意,等等问题都对运维人员的考验。

正文完
 0