提示:文章写完后,目录可以自动生成,如何生成可参考右边的帮助文档

文章目录

  • 前言
  • 一、介绍下MongoDB
    • 1.什么是NoSql数据库?
    • 2.基于文件存储,那么它的存储结构是什么?
    • 3.什么是BSON格式,与JSON的区别,有什么优势?
  • 二、MongoDB与Mysql的区别?
  • 三、说说MongoDB的索引
  • 四、说说MongoDB索引底层原理实现,与mysql有什么区别,有什么优势?
  • 五、说说MongoDB适用哪些场景?如何选择?
    • 1、MongoDB的适用场景
    • 2、你在实际开发中怎么使用MongoDB的?
    • 3、如何选择使用MongoDB?
  • 六、说说MongoDB的数据模型,如何选择?
  • 七、说说MongoDB的存储引擎,有什么优势?
  • 八、如何保证MongoDB高可用?
    • 1、主从复制
    • 2、复制集
    • 3、分片集群
  • 总结

前言

自己整理的MongoDB面试问题,由浅入深


一、介绍下MongoDB

MongoDB 是一款高性能的NoSql数据库,是基于文件存储的数据库,采用BSON格式来存储数据。MongoDB 是一个介于关系数据库和非关系数据库之间的产品,是非关系数据库中功能最丰富、最像关系数据库的。(在高负载的情况下,通过添加更多的节点,可以保证服务器性能)

1.什么是NoSql数据库?

NoSQL=Not Only SQL,支持类似SQL的功能。其性能较高,不使用SQL意味着没有结构化的存储要求(SQL为结构化的查询语句),没有约束之后架构更加灵活。

2.基于文件存储,那么它的存储结构是什么?

一个MongDB数据库是由多个集合(collection)构成的(相当于mysql中的表),每个集合中包含多个文档(document)(相当于mysql中的行),每个文档中包含多个字段(field)(相当于mysql中的列)

3.什么是BSON格式,与JSON的区别,有什么优势?

BSON是一种类json的一种二进制形式的存储格式,简称Binary JSON,它和JSON一样,支持内嵌的文档对象和数组对象,但是BSON有JSON没有的一些数据类型,如Date和Binary Data类型。BSON可以做为网络数据交换的一种存储形式,是一种schema-less的存储形式。

它的优点是灵活性高,但它的缺点是空间利用率不是很理想。

{key:value,key2:value2} 这是一个BSON的例子,其中key是字符串类型,后面的value值,它的类型一般是字符串,double,Array,ISODate等类型。

BSON有三个特点:轻量性、可遍历性、高效性

二、MongoDB与Mysql的区别?

1)从存储结构上看

2)从索引上看两者区别
(1)mysql的索引有唯一索引、主键索引、联合索引、普通索引。MongoDB的索引支持地理位置索引、全文索引、哈希索引。
(2)msyql的主键索引可以指定1到N列作为主键索引,而MongoDB的主键索引指定为_id字段
3)从索引结构上看(见第四部分)

4)适用场景(见第五部分)

三、说说MongoDB的索引

MongoDB的索引共有以下这些:
1、单键索引
支持所有数据类型中的单个字段索引,并且可以在文档的任何字段上定义。
(1)特殊的单键索引----过期索引 TTL ( Time To Live)
TTL索引是MongoDB中一种特殊的索引, 可以支持文档在一定时间之后自动过期删除,目前TTL索引只能在单字段上建立,并且字段类型必须是日期类型。
db.集合名.createIndex({“日期字段”:排序方式}, {expireAfterSeconds: 秒数})
2、复合索引
通常我们需要在多个字段的基础上搜索表/集合,这是非常频繁的。 如果是这种情况,我们可能会考虑在MongoDB中制作复合索引。
创建复合索引时要注意的重要事项包括:字段顺序与索引方向。
db.集合名.createIndex( { “字段名1” : 排序方式, “字段名2” : 排序方式 } )
3、多键索引
针对属性包含数组数据的情况,MongoDB⽀持针对数组中每⼀个element创建索引,Multikey indexes支持strings,numbers和nested documents
4、地理空间索引
针对地理空间坐标数据创建索引。
(1)2dsphere索引,用于存储和查找球面上的点
(2)2d索引,用于存储和查找平面上的点
db.company.ensureIndex( { loc : “2dsphere” } )
5、全文索引
MongoDB提供了针对string内容的文本查询,Text Index支持任意属性值为string或string数组元素的索引查询。
注意:一个集合仅支持最多一个Text Index,中文分词不理想 推荐ES。
db.集合.createIndex({“字段”: “text”})
6、hash索引
针对属性的哈希值进行索引查询,当要使用Hashed index时,MongoDB能够自动的计算hash值,无需程序计算
hash值。注:hash index仅支持等于查询,不支持范围查询。
db.集合.createIndex({“字段”: “hashed”})

四、说说MongoDB索引底层原理实现,与mysql有什么区别,有什么优势?

MySql是关系型数据库,数据的关联性是非常强的,区间访问是常见的一种情况,底层索引组织数据使用B+树,B+树由于数据全部存储在叶子节点,并且通过指针串在一起,这样就很容易的进行区间遍历甚至全部遍历。
MongoDB使用B-树,所有节点都有Data域,只要找到指定索引就可以进行访问,单次查询从结构上来看要快于MySql。

B-树的特点:
(1) 多路 非二叉树
(2) 每个节点 既保存数据 又保存索引
(3) 搜索时 相当于二分查找
B+ 树的特点:
(1) 多路非二叉树
(2) 只有叶子节点保存数据
(3) 搜索时 也相当于二分查找
(4) 增加了 相邻节点指针
从上面我们可以看出最核心的区别主要有俩个,一个是数据的保存位置,一个是相邻节点的指向:
(1)B+树相邻接点的指针可以大大增加区间访问性,可使用在范围查询等,而B-树每个节点 key 和 data 在一起适合随机读写 ,而区间查找效率很差。
(2)B+树更适合外部存储,也就是磁盘存储,使用B-结构的话,每次磁盘预读中的很多数据是用不上的数据。因此,它没能利用好磁盘预读的提供的数据。由于节点内无data 域,每个节点能索引的范围更大更精确。
(3)注意这个区别相当重要,是基于(1)(2)(3)的,B-树每个节点即保存数据又保存索引 树的深度大,所以磁盘IO的次数多,B+树只有叶子节点保存,较B树而言深度小,磁盘IO少,有利于区间访问。

五、说说MongoDB适用哪些场景?如何选择?

1、MongoDB的适用场景

(1)网站数据:MongoDB非常适合实时的插入,更新与查询,并具备网站实时数据存储所需的复制及高度伸缩性。
(2)缓存:由于性能很高,Mongo 也适合作为信息基础设施的缓存层。在系统重启之后,由Mongo 搭建的持久化缓存层可以避免下层的数据源过载。
(3)大尺寸、低价值的数据:使用传统的关系型数据库存储这些大尺寸低价值数据时会比较浪费,在此之前,很多时候程序员往往会选择传统的文件进行存储。
(4)高伸缩性的场景:MongoDB非常适合由数十或数百台服务器组成的数据库,Mongo 的路线图中已经包含对MapReduce 引擎的内置支持以及集群高可用的解决方案。
(5)用于对象及JSON 数据的存储:Mongo 的BSON 数据格式非常适合文档化格式的存储及查询。

2、你在实际开发中怎么使用MongoDB的?

实际开发中主要使用MongoDB做关键业务的日志记录

3、如何选择使用MongoDB?

选择MongoDB场景必须要满足 应用不需要事务及复杂 join支持
并且满足如下数个场景,则可考虑用MongoDB
(1)新应用,需求会变,数据模型无法确定,想快速迭代开发
(2)应用需要2000-3000以上的读写QPS(更高也可以)
(3)应用需要TB甚至PB 级别数据存储
(4)应用发展迅速,需要能快速水平扩展
(5)应用要求存储的数据不丢失
(6)应用需要99.999%高可用
(7)应用需要大量的地理位置查询、文本查询

六、说说MongoDB的数据模型,如何选择?

1)内嵌
内嵌的方式指的是把相关联的数据保存在同一个文档结构之中。MongoDB的文档结构允许一个字段或者一个数组内的值作为一个嵌套的文档。
2)引用
引用方式通过存储数据引用信息来实现两个不同文档之间的关联,应用程序可以通过解析这些数据引用来访问相关数据。

如何选择?
选择内嵌:
1)数据对象之间有包含关系 ,一般是数据对象之间有一对多或者一对一的关系 。
2)需要经常一起读取的数据。
3)有 map-reduce/aggregation 需求的数据放在一起,这些操作都只能操作单个 collection。
选择引用:
1)当内嵌数据会导致很多数据的重复,并且读性能的优势又不足于覆盖数据重复的弊端 。
2)需要表达比较复杂的多对多关系的时候 。
3)大型层次结果数据集 嵌套不要太深。

七、说说MongoDB的存储引擎,有什么优势?

存储引擎是MongoDB的核心组件,负责管理数据如何存储在硬盘和内存上。MongoDB支持的存储引擎有MMAPv1,WiredTiger和InMemory。InMemory存储引擎用于将数据只存储在内存中,只将少量的元数据(meta-data)和诊断日志(Diagnostic)存储到硬盘文件中,由于不需要Disk的IO操作,就能获取所需的数据,InMemory存储引擎大幅度降低了数据查询的延迟(Latency)。从mongodb3.2开始默认的存储引擎是WiredTiger,3.2版本之前的默认存储引擎是MMAPv1,mongodb4.x版本不再支持MMAPv1存储引擎。

WiredTiger存储引擎优势
1)文档空间分配方式
MMAPV1线性存储 采用的是预分配,提前分配好内存,然后将文档放进去 而文档的空间与预分配的空间差值 需要Padding
WiredTiger使用的是BTree存储 ,随时分配随时挂数据
2)并发级别
WiredTiger 文档级别锁 MMAPV1引擎使用表级锁
3)数据压缩
WiredTiger 采用 snappy (默认) 和 zlib ,相比MMAPV1(无压缩) 空间节省数倍。
4)内存使用
WiredTiger 可以指定内存的使用大小。
5)Cache使用
WT引擎使用了二阶缓存WiredTiger Cache, File System Cache来保证Disk上的数据的最终一致性。
而MMAPv1 只有journal 日志。

WiredTiger引擎包含的文件和作用

1)WiredTiger.basecfg: 存储基本配置信息,与 ConfigServer有关系
2)WiredTiger.lock: 定义锁操作
3)able*.wt: 存储各张表的数据
4)WiredTiger.wt: 存储table* 的元数据
5)WiredTiger.turtle: 存储WiredTiger.wt的元数据
6)journal: 存储WAL(Write Ahead Log)

WiredTiger存储引擎实现原理
写请求
WiredTiger的写操作会默认写入Cache ,并持久化到 WAL (Write Ahead Log),每60s或Log文件达到2G做一次checkpoint (当然我们也可以通过在写入时传入 j: true 的参数强制 journal 文件的同步 ,writeConcern { w: , j: , wtimeout: }) 产生快照文件。WiredTiger初始化时,恢复至最新的快照状态,然后再根据WAL恢复数据,保证数据的完整性。
Cache是基于BTree的,节点是一个page,root page是根节点,internal page是中间索引节点,leaf page真正存储数据,数据以page为单位读写。WiredTiger采用Copy on write的方式管理写操作(insert、update、delete),写操作会先缓存在cache里,持久化时,写操作不会在原来的leaf page上进行,而是写入新分配的page,每次checkpoint都会产生一个新的root page。

checkpoint流程
1)对所有的table进行一次checkpoint,每个table的checkpoint的元数据更新至WiredTiger.wt
2)对WiredTiger.wt进行checkpoint,将该table checkpoint的元数据更新至临时文件
WiredTiger.turtle.set
3)将WiredTiger.turtle.set重命名为WiredTiger.turtle。
4)上述过程如果中间失败,WiredTiger在下次连接初始化时,首先将数据恢复至最新的快照状态,然后根据WAL恢复数据,以保证存储可靠性。

Journaling
在数据库宕机时 , 为保证 MongoDB 中数据的持久性,MongoDB 使用了 Write Ahead Logging 向磁盘上的journal文件预先进行写入。除了 journal日志,MongoDB 还使用检查点(checkpoint)来保证数据的一致性,当数据库发生宕机时,我们就需要 checkpoint 和 journal 文件协作完成数据的恢复工作。
1)在数据文件中查找上一个检查点的标识符
2)在 journal 文件中查找标识符对应的记录
3)重做对应记录之后的全部操作

八、如何保证MongoDB高可用?

1、主从复制

master-slave架构中master节点负责数据的读写,slave没有写入权限只负责读取数据。
主从结构没有自动故障转移功能,需要指定master和slave端,不推荐在生产中使用

2、复制集

复制集是由一组拥有相同数据集的mongod实例做组成的集群。
复制集是一个集群,它是2台及2台以上的服务器组成,以及复制集成员包括Primary主节点,secondary从节点和投票节点。
复制集提供了数据的冗余备份,并在多个服务器上存储数据副本,提高了数据的可用性,保证数据的安全性。

为什么要使用复制集?
1)高可用
防止设备(服务器、网络)故障。
提供自动failover 功能。
技术来保证高可用
2)灾难恢复
当发生故障时,可以从其他节点恢复 用于备份。
3)功能隔离
我们可以在备节点上执性能读操作,减少主节点的压力
比如:用于分析、报表,数据挖掘,系统任务等。

复制集集群架构原理
一个复制集中Primary节点上能够完成读写操作,Secondary节点仅能用于读操作。Primary节点需要记录所有改变数据库状态的操作,这些记录保存在 oplog 中,这个文件存储在 local 数据库,各个Secondary节点通过此 oplog 来复制数据并应用于本地,保持本地的数据与主节点的一致。oplog 具有幂等性,即无论执行几次其结果一致,这个比mysql 的二进制日志更好用。

复制集数据同步分为初始化同步和keep复制同步。初始化同步指全量从主节点同步数据,keep复制指初始化同步过后,节点之间的实时同步一般是增量同步
初始化同步有以下两种情况会触发:
(1) Secondary第一次加入。
(2) Secondary落后的数据量超过了oplog的大小,这样也会被全量复制。

MongoDB的Primary节点选举基于心跳触发。一个复制集N个节点中的任意两个节点维持心跳,每个节点维护其他N-1个节点的状态。
心跳检测:
整个集群需要保持一定的通信才能知道哪些节点活着哪些节点挂掉。mongodb节点会向副本集中的其他节点每2秒就会发送一次pings包,如果其他节点在10秒钟之内没有返回就标示为不能访问。每个节点内部都会维护一个状态映射表,表明当前每个节点是什么⻆色、日志时间戳等关键信息。如果主节点发现自己无法与大部分节点通讯则把自己降级为secondary只读节点。

主节点选举触发的时机:
1)第一次初始化一个复制集
2)Secondary节点权重比Primary节点高时,发起替换选举
3)Secondary节点发现集群中没有Primary时,发起选举
4)Primary节点不能访问到大部分(Majority)成员时主动降级

主节点选举是一个二阶段过程+多数派协议
第一阶段:
检测自身是否有被选举的资格 如果符合资格会向其它节点发起本节点是否有选举资格的FreshnessCheck,进行同僚仲裁
第二阶段:
发起者向集群中存活节点发送Elect(选举)请求,仲裁者收到请求的节点会执行一系列合法性检查,如果检查通过,则仲裁者(一个复制集中最多50个节点 其中只有7个具有投票权)给发起者投一票。
pv0通过30秒选举锁防止一次选举中两次投票。
pv1使用了terms(一个单调递增的选举计数器)来防止在一次选举中投两次票的情况。
多数派协议:
发起者如果获得超过半数的投票,则选举通过,自身成为Primary节点。获得低于半数选票的原因,除了常见的网络问题外,相同优先级的节点同时通过第一阶段的同僚仲裁并进入第二阶段也是一个原因。因此,当选票不足时,会sleep[0,1]秒内的随机时间,之后再次尝试选举。

3、分片集群

分片(sharding)是MongoDB用来将大型集合水平分割到不同服务器(或者复制集)上所采用的方法。不需要功能强大的大型计算机就可以存储更多的数据,处理更大的负载。

为什么要分片
1)存储容量需求超出单机磁盘容量。
2)活跃的数据集超出单机内存容量,导致很多请求都要从磁盘读取数据,影响性能。
3)IOPS超出单个MongoDB节点的服务能力,随着数据的增长,单机实例的瓶颈会越来越明显。
4)副本集具有节点数量限制。

分片集群由以下3个服务组成:
Shards Server: 每个shard由一个或多个mongod进程组成,用于存储数据。
Router Server: 数据库集群的请求入口,所有请求都通过Router(mongos)进行协调,不需要在应用程序添加一个路由选择器,Router(mongos)就是一个请求分发中心 它负责把应用程序的请求转发到对应的Shard服务器上。
Config Server: 配置服务器。存储所有数据库元信息(路由、分片)的配置。

分片策略
1)范围分片
范围分片是基于分片主键的值切分数据,每一个区块将会分配到一个范围。
范围分片适合满足在一定范围内的查找,例如查找X的值在[20,30)之间的数据,mongo 路由根据Config server中存储的元数据,可以直接定位到指定的shard的Chunk中。
缺点: 如果shard key有明显递增(或者递减)趋势,则新插入的文档多会分布到同一个chunk,无法扩展写的能力。

2)hash分片
Hash分片是计算一个分片主键的hash值,每一个区块将分配一个范围的hash值。
Hash分片与范围分片互补,能将文档随机的分散到各个chunk,充分的扩展写能力,弥补了范围分片的不足,缺点是不能高效的服务范围查询,所有的范围查询要分发到后端所有的Shard才能找出满足条件的文档。

3)组合分片
数据库中没有比较合适的片键供选择,或者是打算使用的片键基数太小(即变化少如星期只有7天可变化),可以选另一个字段使用组合片键,甚至可以添加冗余字段来组合。一般是粗粒度+细粒度进行组合。

如何合理的选择片键shard key
无非从两个方面考虑,数据的查询和写入,最好的效果就是数据查询时能命中更少的分片,数据写入时能够随机的写入每个分片,关键在于如何权衡性能和负载。


总结

持续更新中。。。。。。

MongoDB面试问题相关推荐

  1. mongodb面试题目,2022腾讯Java面试题精选

    前言 打工人,打工魂,打工都是人上人,记住,打工才是王道,我们都要做打工人.人可以一天不吃饭,但不能一天不打工.打工让我们身心愉悦,节假日是掏空我们的身体.别睡了,打工仔,起床打工吧! --<打 ...

  2. mysql mongodb b树_为何Mongodb索引用B树,而Mysql用B+树?

    引言 很久没写文章了,今天回来重操旧业. 今天讲的这个主题,是<面试官:谈谈你对mysql索引的认识>,里头提到的一个坑.mysql 也就是说,若是面试官问的是,为何Mysql中Innod ...

  3. 2023级安全岗面试题及面试经验分享

    写在前面 个人强烈感觉面试因人而异,对于简历上有具体项目经历的同学,个人感觉面试官会着重让你介绍自己的项目,包括但不限于介绍一次真实攻防/渗透/挖洞/CTF/代码审计的经历 => 因此对于自己的 ...

  4. 2023级网络安全岗面试题及面试经验分享

    在当今社会网络安全行业越来越发达,也有越来越多的人去学习,为了更好地进行工作,除了学好知识外还要应对企业的面试. 所以在这里我归总了一些网络安全方面的常见面试题,希望对大家有所帮助. 一个2023届毕 ...

  5. very very good,Java面试宝典+Java核心知识集

    这几天刚整理出炉的两份最全"Java面试宝典+Java核心知识集"(very very good!!!),因此有了今天咱这篇文章,没错,我又来分享干货了!!! Java面试宝典 说 ...

  6. 22年最强Java面试八股文界的“六边形战士”,堪称天花板!

    不积跬步无以至千里,下面的内容是对网上原有的Java面试题集及答案进行了全面修订之后给出的负责任的题目和答案,原来的题目中有很多重复题目和无价值的题目,还有不少的参考答案也是错误的,修改后的Java面 ...

  7. Java面试八股文界的“六边形战士”22年最强,不接受反驳!

    不积跬步无以至千里,下面的内容是对网上原有的Java面试题集及答案进行了全面修订之后给出的负责任的题目和答案,原来的题目中有很多重复题目和无价值的题目,还有不少的参考答案也是错误的,修改后的Java面 ...

  8. Java年薪30W+面试必问知识之《2020年面试宝典总纲》

    前言 一份月薪30K的java开发岗位工作要求是怎样的呢?面试都会问到哪些呢? 任职要求: 1.计算机或相关专业本科(或以上)学历,具备3年以上Java服务端开发经验,熟悉常用的Java开源框架,如熟 ...

  9. 什么是 MongoDB,为什么它是当今最受欢迎的数据库之一?

    什么是MongoDB? MongoDB 是一个面向文档的 NoSQL 数据库,用于存储大量数据.MongoDB 使用集合和文档,而不是传统关系数据库中的表和行.MongoDB 是一个最早出现在 200 ...

最新文章

  1. CListCtrl创建方法
  2. apache不能能够解析php文件
  3. C/C++语言入门篇 -- 文件操作
  4. xml解析:Sax,Dom,pull解析
  5. springmvc+ueditor上传路径(个人备忘)
  6. [猎豹网校]数据结构与算法_C#语言
  7. android httpclient 设置超时
  8. mysql awr报告生成_批量生成AWR报告(转载总结)
  9. Matlab一维数据的中值滤波与均值滤波函数
  10. Mac Android 查看dex文件内容
  11. Codeforces Round #614 (Div. 2)A. ConneR and the A.R.C. Markland-N
  12. linux cp omitting 复制,Linux中复制目录报错cp:omitting directory的解决办法
  13. Idea的全局搜索快捷键
  14. vue 不同权限显示不同页面
  15. 补天白帽大会五大热点前瞻
  16. css隐藏浏览器的x/y轴
  17. VENUE | S6L初次安装详细视频指南
  18. 大批明星出国避难,大批医生选择逆行,是时候改变我们的价值观了···
  19. discuzapi插件_discuz! api
  20. 禁止windows更新唤醒计算机,windows10睡眠被自动更新唤醒的解决方法

热门文章

  1. math ceil函数python_Python ceil函数
  2. html5 移动游戏,HTML5移动游戏时代到来了!
  3. 比較好的JAVA網站
  4. Iterator 的用法
  5. ShardingSphere 5.2.1 发布|新增系统库、强制分片路由、一致性校验
  6. 加速计算,加速智慧未来
  7. 洛谷P4383 [八省联考2018]林克卡特树lct(DP凸优化/wqs二分)
  8. AnimationPacker重写
  9. 傻子也能看懂的迪杰斯特拉算法(转)
  10. 微任务,宏任务,DOM渲染的执行顺序