Linux操作系统下的MongoDB使用手册

1. 数据库简介

数据库(Database)

数据库是按照数据结构来组织、存储和管理数据的仓库。我们的程序都是在内存中运行的,一旦程序运行结束或者计算机断电,程序运行中的数据都会丢失。所以我们就需要将一些程序运行的数据持久化到硬盘之中,以确保数据的安全性。而数据库就是数据持久化的最佳选择。说白了,数据库就是存储数据的仓库。

数据库分类

  • 关系型数据库(RDBMS, Relational Database Management System, 关系型数据库管理系统)
    • MySQL、Oracle、DB2、SQL Server…
    • 关系数据库中全是表
  • 非关系型数据库(NoSQL,Not Only SQL)
    • MongoDB、Redis…
    • 键值对数据库
    • 文档数据库MongoDB

2. MongoDB简介

MongoDB的特点

  • C++语言编写的,是一个基于分布式文件存储的开源数据库系统;
  • 是为快速开发互联网Web应用而设计的数据库系统;
  • 设计目标是极简、灵活、作为Web应用栈的一部分;
  • 数据模型面向文档,所谓的文档是一种类似JSON的结构,简单理解MongoDB数据库中存储的是各种各样的JSON(BSON, Binary JSON的简写)

MongoDB概念解析

在MongoDB中基本的概念是文档、集合、数据库。

SQL术语/概念 MongoDB术语/概念 解释/说明
database database 数据库
table collection 数据库表/集合
row document 数据记录行/文档
column field 数据字段/域
index index 索引
table joins 表连接, MongoDB不支持
primary key primary key 主键, MongoDB自动将_id字段设置为主键

3. MongoDB安装

MongoDB源码下载地址:https://www.mongodb.com/download-center#community

下载步骤如下图所示:
在这里插入图片描述

下载速度有点慢。。。

本台机器操作系统是Linux CentOS 7.7,首先需要安装平台依赖包

sudo yum install libcurl openssl

解压安装包到/usr/local目录下,并重命名为mongodb

扫描二维码关注公众号,回复: 14637744 查看本文章
tar -zxvf mongodb-linux-x86_64-rhel70-5.0.8.tgz -C /usr/local && mv /usr/local/mongodb-linux-x86_64-rhel70-5.0.8 /usr/local/mongodb

将MongoDB的可执行文件添加到PATH路径中

# 打开/etc/profile文件
vim /etc/profile

# 在最后添加下面一行
export PATH=/usr/local/mongodb/bin:$PATH

# 退出保存文件
:wq

# 再执行一次/etc/profile脚本,让其生效,否则需要重新登录才可以
source /etc/profile 或者 . /etc/profile

在启动MongoDB服务前,创建文件夹

# 数据存储目录
sudo mkdir -p /var/lib/mongodb

# 日志文件目录
sudo mkdir -p /var/log/mongodb

启动服务

mongod --dbpath /var/lib/mongodb --logpath /var/log/mongodb/mongod.log --fork

查看/var/log/mongodb/mongod.log文件

tail -f /var/log/mongodb/mongod.log

出现以下内容证明服务启动成功

在这里插入图片描述

停止服务

mongod --dbpath /var/lib/mongodb --logpath /var/log/mongodb/mongod.log --shutdown

4. 启动MongoDB客户端

由于之前已将MongoDB的可执行文件添加到PATH路径中,所以在任意位置执行mongo即可启动客户端。

在这里插入图片描述

5. MongoDB操作

5.1 创建数据库

MongoDB创建数据库的语法格式如下:

# 如果数据库不存在,则会创建数据库,否则会切换到指定数据库下
use DATABASE_NAME

查看所有数据库

show dbs

查看当前所连接的数据库对象

db

注意:要显示新创建的数据库,需要往里插入一些数据。

实例

例1: 创建名为test01的数据库
在这里插入图片描述

5.2 删除数据库

MongoDB删除数据库的语法格式如下:

db.dropDatabase()

实例

例1: 删除名为test01的数据库
在这里插入图片描述

5.3 创建集合

MongoDB创建集合的语法格式如下:

db.createCollection(name, options)

参数说明:

  • name: 要创建的集合名称
  • options: 可选参数, 指定有关内存大小及索引的选项

options 可以是如下参数:

字段 类型 描述
capped 布尔 (可选)如果为 true,则创建固定集合。固定集合是指有着固定大小的集合,当达到最大值时,它会自动覆盖最早的文档。 当该值为 true 时,必须指定 size 参数。
autoIndexId 布尔 3.2 之后不再支持该参数。(可选)如为 true,自动在 _id 字段创建索引。默认为 false。
size 数值 (可选)为固定集合指定一个最大值,即字节数。 如果 capped 为 true,也需要指定该字段。
max 数值 (可选)指定固定集合中包含文档的最大数量。

实例

例1: test数据库下创建不带参数的集合num01

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4SDr33Dz-1652341435653)(Mongodb.assets/image-20220510154822807.png)]

例2: test数据库下创建集合num02,集合空间大小60000B,文档最大个数1000个

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-JhTS9yvW-1652341435654)(Mongodb.assets/image-20220510155405376.png)]

MongoDB查看已有集合的语法格式如下:

show collections 或 show tables

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ku0i52nR-1652341435655)(Mongodb.assets/image-20220510155903137.png)]

5.4 删除集合

MongoDB删除集合的语法格式如下:

db.collection.drop()

如果成功删除选定集合,则 drop() 方法返回 true,否则返回 false。

实例

例1: 删除test数据库下名为num01的集合

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-zCLhsgvX-1652341435656)(Mongodb.assets/image-20220510161328765.png)]

5.5 插入文档

MongoDB中所有存储在集合中的数据都是 BSON 格式,BSON 是一种类似 JSON 的二进制形式的存储格式,是 Binary JSON 的简称。

MongoDB插入一条文档的语法格式如下:

db.collection.insertOne(
   <document>,
   {
    
    
      writeConcern: <document>
   }
) 

参数说明:

  • document:要写入的文档。

  • writeConcern:写入策略,包括3个配置项{ w: <value>, j: <boolean>, wtimeout: <number> }

    • w的取值可以是0,即不关心是否写入成功;也可以是1~集群最大数据节点数,即写操作要被确认同步到指定节点数才算成功;默认值为 1
    • j参数表示是否写操作要进行journal(日志)持久化之后才向用户确认;{j: true} 要求primary写操作进行了journal持久化之后才向用户确认;{j: false} 只要求写操作已经在journal(日志)缓存中即可向用户确认,journal后续会将持久化到磁盘,默认是100ms。
    • wtimeout参数指定一个时间限制,以防止写操作无限制被阻塞导致无法应答给客户端。

MongoDB插入多条文档的语法格式如下:

db.collection.insertMany(
   [ <document 1> , <document 2>, ... ],
   {
    
    
      writeConcern: <document>,
      ordered: <boolean>
   }
)

参数说明:

  • document:要写入的文档。
  • writeConcern:写入策略,包括3个配置项{ w: <value>, j: <boolean>, wtimeout: <number> }
    • w的取值可以是0,即不关心是否写入成功;也可以是1~集群最大数据节点数,即写操作要被确认同步到指定节点数才算成功;默认值为 1
    • j参数表示是否写操作要进行journal(日志)持久化之后才向用户确认;{j: true} 要求primary写操作进行了journal持久化之后才向用户确认;{j: false} 只要求写操作已经在journal(日志)缓存中即可向用户确认,journal后续会将持久化到磁盘,默认是100ms。
    • wtimeout参数指定一个时间限制,以防止写操作无限制被阻塞导致无法应答给客户端。
  • ordered:指定是否按顺序写入,默认 true,按顺序写入。

实例

例1: 插入一条文档

db.num02.insertOne({
    
    "key1":1})

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-hDQKmiie-1652341435657)(Mongodb.assets/image-20220510212028011.png)]

例2: 插入多条文档

db.num02.insertMany([{
    
    "key2":2},{
    
    "key3":3}])

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-njBasRWE-1652341435658)(Mongodb.assets/image-20220510212635297.png)]

5.6 更新文档

MongoDB 使用 update() 和 save() 方法来更新集合中的文档。接下来让我们详细来看下两个函数的应用及其区别。

5.6.1 update()方法

update() 方法用于更新已存在的文档。语法格式如下:

db.collection.update(
   <query>,
   <update>,
   {
    
    
     upsert: <boolean>,
     multi: <boolean>,
     writeConcern: <document>
   }
)

参数说明:

  • query :update的查询条件,类似sql update查询内where后面的。
  • update:update的对象和一些更新的操作符(如 , , ,inc…)等,也可以理解为sql update查询内set后面的
  • upsert:可选,这个参数的意思是,如果不存在update的记录,是否插入objNew,true为插入,默认是false,不插入。
  • multi:可选,mongodb 默认是false,只更新找到的第一条记录,如果这个参数为true,就把按条件查出来多条记录全部更新。
  • writeConcern:更新策略,包括3个配置项{ w: <value>, j: <boolean>, wtimeout: <number> }
    • w的取值可以是0,即不关心是否更新成功;也可以是1~集群最大数据节点数,即更新操作要被确认同步到指定节点数才算成功;默认值为 1
    • j参数表示是否更新操作要进行journal(日志)持久化之后才向用户确认;{j: true} 要求primary更新操作进行了journal持久化之后才向用户确认;{j: false} 只要求更新操作已经在journal(日志)缓存中即可向用户确认,journal后续会将持久化到磁盘,默认是100ms。
    • wtimeout参数指定一个时间限制,以防止更新操作无限制被阻塞导致无法应答给客户端。

实例

例1: 更新查找到的第一条title为"MongoDB教程"的文档为"MongoDB"

# 在test数据库下创建集合num01
db.createCollection("num01")

# 往集合num01下插入多条数据
db.num01.insertMany([
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 99
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 88
}])

# 更新查找到的第一条title为"MongoDB教程"的文档为"MongoDB"
db.num01.update({
    
    'title':'MongoDB教程'},{
    
    $set:{
    
    'title':'MongoDB'}},{
    
    'writeConcern':{
    
    'w':0,'j':true}})

# 查看是否更新成功
db.num01.find().pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-xVHM1FKB-1652341435659)(Mongodb.assets/image-20220511105800090.png)]

以上语句只会修改第一条发现的文档,如果你要修改多条相同的文档,则需要设置 multi 参数为 true。

例2: 更新查找到的所有title为"MongoDB教程"的文档为"MongoDB"

# 更新查找到的所有title为"MongoDB教程"的文档为"MongoDB"
db.num01.update({
    
    'title':'MongoDB教程'},{
    
    $set:{
    
    'title':'MongoDB'}},{
    
    multi:true})

# 查看是否更新成功
db.num01.find().pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-lxRJZFjm-1652341435660)(Mongodb.assets/image-20220511110042683.png)]

5.6.2 save()方法

save() 方法通过传入的文档来替换已有文档,_id 主键存在就更新,不存在就插入。语法格式如下:

db.collection.save(
   <document>,
   {
    
    
     writeConcern: <document>
   }
)

参数说明:

  • document : 文档数据。
  • writeConcern : 更新策略,包括3个配置项{ w: <value>, j: <boolean>, wtimeout: <number> }
    • w的取值可以是0,即不关心是否更新成功;也可以是1~集群最大数据节点数,即更新操作要被确认同步到指定节点数才算成功;默认值为 1
    • j参数表示是否更新操作要进行journal(日志)持久化之后才向用户确认;{j: true} 要求primary更新操作进行了journal持久化之后才向用户确认;{j: false} 只要求更新操作已经在journal(日志)缓存中即可向用户确认,journal后续会将持久化到磁盘,默认是100ms。
    • wtimeout参数指定一个时间限制,以防止更新操作无限制被阻塞导致无法应答给客户端。

实例

例1: 替换num03集合中_id为627a6ed7d380f74ddad18d3f的文档数据:

db.num03.save({
    
    
    "_id" : ObjectId("627a6ed7d380f74ddad18d3f"),
    "title" : "MongoDB",
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 66
})

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-B8SGojYA-1652341435662)(Mongodb.assets/image-20220510220845196.png)]

5.7 删除文档

MongoDB删除文档的语法格式如下:

db.collection.remove(
   <query>,
   {
    
    
     justOne: <boolean>,
     writeConcern: <document>
   }
)

参数说明:

  • query :(可选)删除的文档的条件。
  • justOne : (可选)如果设为 true 或 1,则只删除一个文档,如果不设置该参数,或使用默认值 false,则删除所有匹配条件的文档。
  • writeConcern : 删除策略,包括3个配置项{ w: <value>, j: <boolean>, wtimeout: <number> }
    • w的取值可以是0,即不关心是否写入成功;也可以是1~集群最大数据节点数,即删除操作要被确认同步到指定节点数才算成功;默认值为 1
    • j参数表示是否删除操作要进行journal(日志)持久化之后才向用户确认;{j: true} 要求primary删除操作进行了journal持久化之后才向用户确认;{j: false} 只要求删除操作已经在journal(日志)缓存中即可向用户确认,journal后续会将持久化到磁盘,默认是100ms。
    • wtimeout参数指定一个时间限制,以防止删除操作无限制被阻塞导致无法应答给客户端。

实例

例1: 删除“num02”集合下查找到的所有title为"MongoDB教程"的文档

# 在test数据库下创建集合num02
db.createCollection("num02")

# 往集合num02下插入多条数据
db.num02.insertMany([
{
    
    
    title: 'MongoDB', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 99
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 88
}])

# 删除“num02”集合下所有title为"MongoDB教程"的文档
db.num02.remove({
    
    'title':'MongoDB教程'})

# 查看是否删除成功
db.num02.find().pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-3dGEbCro-1652341435663)(Mongodb.assets/image-20220511143226969.png)]

5.8 查询文档

MongoDB 查询数据的语法格式如下:

# pretty()方法以易读的方式来显示所有文档。
db.collection.find(query, projection).pretty()

参数说明:

  • query :可选,使用查询操作符指定查询条件
  • projection :可选,使用投影操作符指定返回的键。查询时返回文档中所有键值, 只需省略该参数即可(默认省略)。

补充说明:

  • 若不指定 projection,则默认返回所有键,指定 projection 格式如下,有两种模式(两种模式不可混用)
  • _id字段比较特殊,它不受两种模式的影响,由1和0来决定是否返回
db.collection.find(query, {
    
    key1: 1, key2: 1}) # inclusion模式 指定返回的键,不返回其他键
db.collection.find(query, {
    
    key1: 0, key2: 0}) # exclusion模式 指定不返回的键,返回其他键
db.collection.find(query, {
    
    key1: 1, _id: 0}) # 语句合法

5.8.1 AND与OR操作符

MongoDB的AND条件与OR条件的语法格式如下:

# MongoDB AND条件
db.col.find({
    
    key1:value1, key2:value2}).pretty()

# MongoDB OR条件
>db.col.find(
   {
    
    
      $or: [
         {
    
    key1: value1}, {
    
    key2:value2}
      ]
   }
).pretty()

实例

例1: 查找“num02”集合下所有title为"MongoDB教程",且likes为100的文档

# 在test数据库下创建集合num02
db.num02.drop()
db.createCollection("num02")

# 往集合num02下插入多条数据
db.num02.insertMany([
{
    
    
    title: 'MongoDB', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 99
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 88
}])

# 查找“num02”集合下所有title为"MongoDB",且likes为100的文档
db.num02.find({
    
    "title": "MongoDB", "likes": 100}).pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-6vNILymf-1652341435664)(Mongodb.assets/image-20220511144357054.png)]

例2: 查找“num02”集合下所有likes为100或88的文档

# 在例1的基础上执行以下命令,查找“num02”集合下所有likes为100或88的文档
db.num02.find({
    
    
	$or: [
		{
    
    "likes": 100}, {
    
    "likes": 88}
	]
}).pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-ZsGrXNTt-1652341435665)(Mongodb.assets/image-20220511145014101.png)]

5.8.2 条件操作符

MongoDB与RDBMS(Relational Database Management System, 关系型数据库管理系统)中条件操作符的比较如下:

操作 格式 范例 RDBMS中的类似语句
等于 {<key>:<value>} db.col.find({"by":"菜鸟教程"}).pretty() Select * from col where by = '菜鸟教程'
小于 {<key>:{$lt:<value>}} db.col.find({"likes":{$lt:50}}).pretty() Select * from col where likes < 50
小于或等于 {<key>:{$lte:<value>}} db.col.find({"likes":{$lte:50}}).pretty() Select * from col where likes <= 50
大于 {<key>:{$gt:<value>}} db.col.find({"likes":{$gt:50}}).pretty() Select * from col where likes > 50
大于或等于 {<key>:{$gte:<value>}} db.col.find({"likes":{$gte:50}}).pretty() Select * from col where likes >= 50
不等于 {<key>:{$ne:<value>}} db.col.find({"likes":{$ne:50}}).pretty() Select * from col where likes != 50

实例

例1: 查找“num03”集合下所有likes为100的文档

# 在test数据库下创建集合num03
db.num03.drop()
db.createCollection("num03")

# 往集合num03下插入多条数据
db.num03.insertMany([
{
    
    
    title: 'MongoDB', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 99
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 98
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 97
}])

# 查找“num03”集合下所有likes为100的文档
db.num03.find({
    
    "likes": 100}).pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FLCC7EDo-1652341435666)(Mongodb.assets/image-20220511151158837.png)]

例2: 查找“num03”集合下所有likes大于等于98且小于100的文档

# 在例1的基础上执行以下命令,查找“num03”集合下所有likes大于等于98且小于100的文档
db.num03.find({
    
    "likes": {
    
    $gte: 98,$lt: 100}}).pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-IDqcK8gF-1652341435667)(Mongodb.assets/image-20220511153505039.png)]

5.8.3 $type操作符

$type操作符是基于BSON类型来检索集合中匹配的数据类型,并返回结果。

MongoDB 中可以使用的类型如下表所示:

类型 数字 备注
Double 1
String 2
Object 3
Array 4
Binary data 5
Undefined 6 已废弃。
Object id 7
Boolean 8
Date 9
Null 10
Regular Expression 11
JavaScript 13
Symbol 14
JavaScript (with scope) 15
32-bit integer 16
Timestamp 17
64-bit integer 18
Min key 255 Query with -1.
Max key 127

实例

例1: 查找“num03”集合下所有title为string类型的文档

# 在test数据库下创建集合num03
db.num03.drop()
db.createCollection("num03")

# 往集合num03下插入多条数据
db.num03.insertMany([
{
    
    
    title: 'MongoDB', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 11, 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
}])

# 查找“num03”集合下所有title为string类型的文档
db.num03.find({
    
    "title" : {
    
    $type : 'string'}}).pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-nWNLt1yn-1652341435668)(Mongodb.assets/image-20220511155540287.png)]

5.8.4 Limit与Skip方法

MongoDB的limit()方法接受一个数字参数,该参数可指定从MongoDB中读取的记录条数。

limit()方法基本语法如下所示:

db.COLLECTION_NAME.find().pretty().limit(NUMBER)

MongoDB的skip()方法用于跳过指定数量的数据,skip方法同样接受一个数字参数作为跳过的记录条数。

skip()方法基本语法如下所示:

db.COLLECTION_NAME.find().limit(NUMBER).skip(NUMBER)

实例

例1: 查找“num03”集合中两条likes为100的文档

# 在test数据库下创建集合num03
db.num03.drop()
db.createCollection("num03")

# 往集合num03下插入多条数据
db.num03.insertMany([
{
    
    
    title: 'MongoDB', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 98
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 97
}])

# 查找“num03”集合下两条likes为100的文档
db.num03.find({
    
    "likes": 100}).pretty().limit(2)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-tbTnW3us-1652341435670)(Mongodb.assets/image-20220511205429671.png)]

例2: 查找“num03”集合中第二条likes为100的文档

# 在例1的基础上查找“num03”集合下第二条likes为100的文档
db.num03.find({
    
    "likes": 100}).pretty().limit(1).skip(1)

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-NyrLjzuQ-1652341435671)(Mongodb.assets/image-20220511205921739.png)]

5.8.5 排序

MongoDB的sort()方法可以通过参数指定排序的字段,并使用1和-1来指定排序的方式,其中1为升序排列,而-1是用于降序排列。

sort()方法基本语法如下所示:

db.COLLECTION_NAME.find().sort({
    
    KEY:1})

实例

例1: 查找“num03”集合中全部文档,并以likes字段值升序返回结果

# 在test数据库下创建集合num03
db.num03.drop()
db.createCollection("num03")

# 往集合num03下插入多条数据
db.num03.insertMany([
{
    
    
    title: 'MongoDB', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 99
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 98
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 97
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 96
}])

# 查找“num03”集合中全部文档,并以likes字段值升序返回结果
db.num03.find().pretty().sort({
    
    "likes": 1})

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-FViRqB4y-1652341435672)(Mongodb.assets/image-20220511210918393.png)]

5.9 索引

索引通常能够极大的提高查询的效率,如果没有索引,MongoDB在读取数据时必须扫描集合中的每个文件并选取那些符合查询条件的记录。这种扫描全集合的查询效率是非常低的,特别在处理大量的数据时,查询可以要花费几十秒甚至几分钟,这对网站的性能是非常致命的。索引是特殊的数据结构,索引存储在一个易于遍历读取的数据集合中,索引是对数据库表中一列或多列的值进行排序的一种结构。

MongoDB关于索引操作的基本语法格式如下所示:

# 创建一个或多个索引
db.collection.createIndex(keys, options)

# 查看集合索引
db.collection.getIndexes()

# 查看集合索引大小
db.collection.totalIndexSize()

# 删除集合所有索引
db.collection.dropIndexes()

# 删除集合指定索引
db.collection.dropIndex("索引名称")

语法中key值为你要创建的索引字段,1为指定按升序创建索引,如果你想按降序来创建索引指定为-1即可;options列表如下:

Parameter Type Description
background Boolean 建索引过程会阻塞其它数据库操作,background可指定以后台方式创建索引,即增加 “background” 可选参数。 “background” 默认值为false
unique Boolean 建立的索引是否唯一。指定为true创建唯一索引。默认值为false.
name string 索引的名称。如果未指定,MongoDB通过连接索引的字段名和排序顺序生成一个索引名称。
dropDups Boolean **3.0+版本已废弃。**在建立唯一索引时是否删除重复记录,指定 true 创建唯一索引。默认值为 false.
sparse Boolean 对文档中不存在的字段数据不启用索引;这个参数需要特别注意,如果设置为true的话,在索引字段中不会查询出不包含对应字段的文档.。默认值为 false.
expireAfterSeconds integer 指定一个以秒为单位的数值,完成 TTL设定,设定集合的生存时间。
v index version 索引的版本号。默认的索引版本取决于mongod创建索引时运行的版本。
weights document 索引权重值,数值在1到99,999之间,表示该索引相对于其他索引字段的得分权重。
default_language string 对于文本索引,该参数决定了停用词及词干和词器的规则的列表。 默认为英语
language_override string 对于文本索引,该参数指定了包含在文档中的字段名,语言覆盖默认的language,默认值为 language.

实例

例1: 在“num03”集合中以_id字段和likes字段建立索引,其中_id字段降序,likes字段升序

# 在test数据库下创建集合num03
db.num03.drop()
db.createCollection("num03")

# 往集合num03下插入多条数据
db.num03.insertMany([
{
    
    
    title: 'MongoDB', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 99
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 98
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 97
},
{
    
    
    title: 'MongoDB教程', 
    description: 'MongoDB是一个Nosql数据库',
    by: 'Smile',
    url: 'http://www.study.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 96
}])

# 在“num03”集合中以_id字段和likes字段建立索引,其中_id字段降序,likes字段升序
db.num03.createIndex({
    
    "_id":-1,"likes":1})

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-4UMWmx9u-1652341435673)(Mongodb.assets/image-20220511214307040.png)]

5.10 聚合

5.10.1 常规聚合

MongoDB 中聚合(aggregate)主要用于处理数据(诸如统计平均值,求和等),并返回计算后的数据结果,有点类似 SQL 语句中的 count(*)

aggregate() 方法的基本语法格式如下所示:

db.COLLECTION_NAME.aggregate(AGGREGATE_OPERATION)

聚合表达式如下表所示:

表达式 描述 实例
$sum 计算总和。 db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$sum : "$likes"}}}])
$avg 计算平均值 db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$avg : "$likes"}}}])
$min 获取集合中所有文档对应值得最小值。 db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$min : "$likes"}}}])
$max 获取集合中所有文档对应值得最大值。 db.mycol.aggregate([{$group : {_id : "$by_user", num_tutorial : {$max : "$likes"}}}])
$push 将值加入一个数组中,不会判断是否有重复的值。 db.mycol.aggregate([{$group : {_id : "$by_user", url : {$push: "$url"}}}])
$addToSet 将值加入一个数组中,会判断是否有重复的值,若相同的值在数组中已经存在了,则不加入。 db.mycol.aggregate([{$group : {_id : "$by_user", url : {$addToSet : "$url"}}}])
$first 根据资源文档的排序获取第一个文档数据。 db.mycol.aggregate([{$group : {_id : "$by_user", first_url : {$first : "$url"}}}])
$last 根据资源文档的排序获取最后一个文档数据 db.mycol.aggregate([{$group : {_id : "$by_user", last_url : {$last : "$url"}}}])

实例

例1: 计算“num03”集合中每个作者所写的文章数

# 在test数据库下创建集合num03
db.num03.drop()
db.createCollection("num03")

# 往集合num03下插入多条数据
db.num03.insertMany([
{
    
    
    title: 'MongoDB Overview', 
    description: 'MongoDB is no sql database',
    by_user: 'runoob.com',
    url: 'http://www.runoob.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'NoSQL Overview', 
    description: 'No sql database is very fast',
    by_user: 'runoob.com',
    url: 'http://www.runoob.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 10
},
{
    
    
    title: 'Neo4j Overview', 
    description: 'Neo4j is no sql database',
    by_user: 'Neo4j',
    url: 'http://www.neo4j.com',
    tags: ['neo4j', 'database', 'NoSQL'],
    likes: 750
}])

# 计算“num03”集合中每个作者所写的文章数
db.num03.aggregate([{
    
    $group : {
    
    _id : "$by_user", num_tutorial : {
    
    $sum : 1}}}])

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-qACJbVID-1652341435675)(Mongodb.assets/image-20220512144739379.png)]

例2: 计算“num03”集合中每个作者所写的文章likes的平均值

# 在例1的基础上,计算“num03”集合中每个作者所写的文章likes的平均值
db.num03.aggregate([{
    
    $group : {
    
    _id : "$by_user", avg_likes : {
    
    $avg : "$likes"}}}])

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-JjWt1rkX-1652341435675)(Mongodb.assets/image-20220512144800137.png)]

例3: 计算“num03”集合中每个作者所拥有的url集合,集合里的值允许重复

# 在例1的基础上,利用下面的语句计算“num03”集合中每个作者所拥有的url集合,且集合里的值允许重复
db.num03.aggregate([{
    
    $group : {
    
    _id : "$by_user", url : {
    
    $push: "$url"}}}])

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-75ayr6Sb-1652341435677)(Mongodb.assets/image-20220512145350182.png)]

5.10.2 聚合管道

管道在Unix和Linux中一般用于将当前命令的输出结果作为下一个命令的参数。MongoDB的聚合管道将MongoDB文档在一个管道处理完毕后将结果传递给下一个管道处理。管道操作是可以重复的。

这里我们介绍一下聚合框架中常用的几个操作:

  • $project:修改输入文档的结构。可以用来重命名、增加或删除域,也可以用于创建计算结果以及嵌套文档。
  • m a t c h :用于过滤数据,只输出符合条件的文档。 match:用于过滤数据,只输出符合条件的文档。 match:用于过滤数据,只输出符合条件的文档。match使用MongoDB的标准查询操作。
  • $limit:用来限制MongoDB聚合管道返回的文档数。
  • $skip:在聚合管道中跳过指定数量的文档,并返回余下的文档。
  • $unwind:将文档中的某一个数组类型字段拆分成多条,每条包含数组中的一个值。
  • $group:将集合中的文档分组,可用于统计结果。
  • $sort:将输入文档排序后输出。
  • $geoNear:输出接近某一地理位置的有序文档。

实例

例1: $project实例

# 在test数据库下创建集合num03
db.num03.drop()
db.createCollection("num03")

# 往集合num03下插入多条数据
db.num03.insertMany([
{
    
    
    title: 'MongoDB Overview', 
    description: 'MongoDB is no sql database',
    by_user: 'runoob.com',
    url: 'http://www.runoob.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 100
},
{
    
    
    title: 'NoSQL Overview', 
    description: 'No sql database is very fast',
    by_user: 'runoob.com',
    url: 'http://www.runoob.com',
    tags: ['mongodb', 'database', 'NoSQL'],
    likes: 10
},
{
    
    
    title: 'Neo4j Overview', 
    description: 'Neo4j is no sql database',
    by_user: 'Neo4j',
    url: 'http://www.neo4j.com',
    tags: ['neo4j', 'database', 'NoSQL'],
    likes: 750
}])

# 让返回结果只包含_id,title,by_user三个字段
db.num03.aggregate(
    {
    
     $project : {
    
    
        title : 1 ,
        by_user : 1 ,
    }}
 ).pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-wiLy3uOx-1652341435678)(Mongodb.assets/image-20220512151111507.png)]

例2: $match实例

# 在例1的基础上,执行以下语句统计likes大于5且小于等于110的文档个数
db.num03.aggregate(
	[
     	{
    
    $match: {
    
    likes: {
    
     $gt :5,$lte: 110}}},
     	{
    
    $group: {
    
    _id: null, count: {
    
    $sum: 1}}}
    ]
).pretty()

[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-udUx58FB-1652341435679)(Mongodb.assets/image-20220512152433289.png)]
例3: $skip实例

# 在例1的基础上,执行以下语句,可跳过第一个文档
db.num03.aggregate(
    {
    
     $skip : 1 }
).pretty()

在这里插入图片描述
参考资料

  1. MongoDB|菜鸟教程 https://www.runoob.com/mongodb/mongodb-tutorial.html

猜你喜欢

转载自blog.csdn.net/weixin_43934075/article/details/124732807