您的位置:首页 > 数据库 > Mongodb

MongoDB中文档的插入,删除,更新,查询(重点)(六)

weixin_43113679 2019-06-10 23:04 85 查看
版权声明:如需转载,请写明出处 https://blog.csdn.net/weixin_43113679/article/details/91408665

文档的数据结构和 JSON 基本一样。
所有存储在集合中的数据都是 BSON 格式。
BSON 是一种类似 JSON 的二进制形式的存储格式,是 Binary JSON 的简称。

1.插入文档

MongoDB 使用 insert()save() 方法向集合中插入文档,语法如下:
先看insert()

db.collection.insert(document)   //collection代表的是集合名

测试

> db.col.insert({title:"MongoDB",name:"网易"})   //插入一个文档
WriteResult({ "nInserted" : 1 })
> db.col.find()   //查询当前集合下的文档,显然成功了
{ "_id" : ObjectId("5cfdf3effe3b41c77086d5fc"), "title" : "MongoDB", "name" : "网易" }

也可以把数据定义一个变量

> document=({title:"ssss",name:"sss"})  //把数据定义为一个变量
{ "title" : "ssss", "name" : "sss" }
> db.col.insert(document)   //插入这个变量
WriteResult({ "nInserted" : 1 })
> db.col.find()
{ "_id" : ObjectId("5cfdf3effe3b41c77086d5fc"), "title" : "MongoDB", "name" : "网易" }
{ "_id" : ObjectId("5cfdf452fe3b41c77086d5fd"), "title" : "ssss", "name" : "sss" }

这样就成功了
对于save() 的用法可以指定 _id 字段,

  • 如果不指定 _id字段那和insert() 是一样的用法了,
  • 如果指定 _id 字段,则会更新该 _id 的数据。

关于save() 的具体用法将在下面的更新文档处演示
3.2 版本后还有以下几种语法可用于插入文档:

  • db.collection.insertOne():向指定集合中插入一条文档数据
> db.col.insertOne({"name":"天下"})
{
"acknowledged" : true,
"insertedId" : ObjectId("5cffb763f9cbc6b3d3d3fe9d")
}
  • db.collection.insertMany():向指定集合中插入多条文档数据(里面有中括号)
> db.col.insertMany([{"name":"腾讯"},{"name":"阿里"}])
{
"acknowledged" : true,
"insertedIds" : [
ObjectId("5cffb80ef9cbc6b3d3d3fe9e"),
ObjectId("5cffb80ef9cbc6b3d3d3fe9f")
]
}

2.删除文档

MongoDB remove()函数是用来移除集合中的数据。
在执行 remove() 函数前先执行 find() 命令来判断执行的条件是否正确,这是一个比较好的习惯。
现在remove() 已经过时了,现在官方推荐 deleteOne()deleteMany()

语法:(2.6版本后的)

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

参数说明

  • query :(可选)删除的文档的条件。
  • justOne : (可选)如果设为 true 或 1,则只删除一个文档,如果不设置该参数,或使用默认值 false,则删除所有匹配条件的文档。
  • writeConcern :(可选)抛出异常的级别。
  • collation – 可选参数,指定用于操作的collation。

测试
专门添加了两个除了_id不同的,其他都相同的来测试

> db.col.find()
{ "_id" : ObjectId("56066169ade2f21f36b03137"), "title" : "MongoDB 教程", "description" : "MongoDB 是一个 Nosql 数据库", "by" : "菜鸟教程", "url" : "http://www.runoob.com", "tags" : [ "mongodb", "database", "NoSQL" ], "likes" : 100 }
{ "_id" : ObjectId("5606616dade2f21f36b03138"), "title" : "MongoDB 教程", "description" : "MongoDB 是一个 Nosql 数据库", "by" : "菜鸟教程", "url" : "http://www.runoob.com", "tags" : [ "mongodb", "database", "NoSQL" ], "likes" : 100 }

删除某字段是什么的文档(准确查找)
接下来删除上面新添加的两个,根据title来删除

>db.col.remove({'title':'MongoDB 教程'})
WriteResult({ "nRemoved" : 2 })           # 删除了两条数据
>db.col.find()
>

如果你只是想删除第一条找到的记录可以设置为justOne为1,

> db.col.remove({'title':'MongoDB 教程'}},1)

当然还有删除此集合全部的文档

>db.col.remove({})
>db.col.find()
>
>> show tables
col  							//此集合还存在
first
runoob

说明用remove() 就算把全部的文档都删除了,但是集合还是存在的

deleteOne()只删除第一个匹配的

语法

db.collection.deleteOne(
<filter>,
{
writeConcern: <document>,
collation: <document>
}
)

测试

> db.col.deleteOne({"公司":"字节"})
{ "acknowledged" : true, "deletedCount" : 1 }

deleteMany()删除所有 匹配到

语法

db.collection.deleteMany(
<filter>,
{
writeConcern: <document>,
collation: <document>
}
)

测试

db.col.deleteMany({"name":"腾讯"})

看起来remove对于deleteOnedeleteMany来说更像是结合体

3.更新文档

MongoDB 使用 update()save() 方法来更新集合中的文档,save() 还可以插入文档,正好上文有save() 没有具体用法,在这一起

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 :可选,抛出异常的级别

测试
先插入一条数据

> db.col.find()
> db.col.insert({"title":"MongoDB教程","name":"李华"})
WriteResult({ "nInserted" : 1 })

通过update() 的方法来更新title

> db.col.update({"title":"MongoDB教程"},{$set:{"title":"MongoDB"}})
//也可以写成  db.col.update({"name":"天意"},{"name":"MongoDB"} )
//不用·加·$set,不过建议加上,因为它是一个关键字
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
> db.col.find().pretty() 			//pretty()让文档按下面这种格式展现,而不是一行
{
"_id" : ObjectId("5cfe32c9fe3b41c77086d5ff"),
"title" : "MongoDB",
"name" : "李华"
}

可以看到title由原来的“MongoDB教程” 变成了“MongoDB”

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

>db.col.update({"title":"MongoDB 教程"},{$set:{"title":"MongoDB"}},{multi:true})

注意
当使用update时,前面第一个大括号可以为空
例子
先查看当前集合的文档

> db.col.find()
{ "_id" : ObjectId("5cfe32c9fe3b41c77086d5ff"), "name" : "MongoDB" }
{ "_id" : ObjectId("5cfe6873fe3b41c77086d600") }
{ "_id" : ObjectId("5cffb763f9cbc6b3d3d3fe9d"), "name" : "京东" }
{ "_id" : ObjectId("5cffb80ef9cbc6b3d3d3fe9e"), "name" : "腾讯" }
{ "_id" : ObjectId("5cffb80ef9cbc6b3d3d3fe9f"), "name" : "阿里" }

第一个大括号为空

> db.col.update({},{"公司":"字节"})
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
> db.col.find()
{ "_id" : ObjectId("5cfe32c9fe3b41c77086d5ff"), "公司" : "字节" }
{ "_id" : ObjectId("5cfe6873fe3b41c77086d600") }
{ "_id" : ObjectId("5cffb763f9cbc6b3d3d3fe9d"), "name" : "京东" }
{ "_id" : ObjectId("5cffb80ef9cbc6b3d3d3fe9e"), "name" : "腾讯" }
{ "_id" : ObjectId("5cffb80ef9cbc6b3d3d3fe9f"), "name" : "阿里" }

db.col.update({},{“公司”:“字节”}) 语句第一个条件虽然没写,但是它会默认搜索全部,并且修改第一个文档,并把第一个文档里除了ObjectId不变,其他的都替换掉

save()方法

通过传入的文档来替换已有文档
语法格式

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

参数说明

  • document : 文档数据。
  • writeConcern :可选,抛出异常的级别。

测试
db.collection.save({}) 里面没有数据会怎么样?

> db.col.find().pretty(){
"_id" : ObjectId("5cfe32c9fe3b41c77086d5ff"),
"title" : "MongoDB",
"name" : "李华"
}
> db.col.save({})
WriteResult({ "nInserted" : 1 })
> db.col.find().pretty(){
"_id" : ObjectId("5cfe32c9fe3b41c77086d5ff"),
"title" : "MongoDB",
"name" : "李华"
}
{ "_id" : ObjectId("5cfe6873fe3b41c77086d600") }

添加了一个文档,里面只有一个生成的ObjectId
开始save更新文档
以下实例中我们替换了 _id 为 5cfe32c9fe3b41c77086d5ff 的文档数据:

> db.col.save({"_id":ObjectId("5cfe32c9fe3b41c77086d5ff"),"name":"天意"})  //根据ObjectId来找到哪个文档
WriteResult({ "nMatched" : 1, "nUpserted" : 0, "nModified" : 1 })
> db.col.find().pretty(){ "_id" : ObjectId("5cfe32c9fe3b41c77086d5ff"), "name" : "天意" }
{ "_id" : ObjectId("5cfe6873fe3b41c77086d600") }

这样saveupdate替换文档的区别就出来了,

  • save:替换的是整个文档,根据 _id 来替换整个文档,对整个文档有影响,如有更新的字段不存在就添加上,存在的就覆盖,如果原文档存在而更新的文档不存在的字段则删除
  • update:替换的字段的值,对其他字段没影响,适合已经存在的文档

4.查询

MongoDB 查询文档使用 find() 方法。
find() 方法以非结构化的方式来显示所有文档。
语法

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

如果你需要以易读的方式来读取数据,可以在find() 后加pretty()

db.col.find().pretty()

pretty() 方法以格式化的方式来显示所有文档。
测试

> db.col.find().pretty(){ "_id" : ObjectId("5cfe32c9fe3b41c77086d5ff"), "name" : "天意" }
{ "_id" : ObjectId("5cfe6873fe3b41c77086d600") }

还有一个findOne(),只返回一个文档

> db.col.findOne()
{ "_id" : ObjectId("5cfe32c9fe3b41c77086d5ff"), "name" : "天意" }

但是,不存在findOne().pretty()

> db.col.findOne().pretty()
2019-06-10T22:52:11.406+0800 E QUERY    [js] TypeError: db.col.findOne(...).pretty is not a function :
@(shell):1:1

返回的是第一个文档,不是随机返回一个文档

5、find()运用关键字来实现某些特定的查询

(1)AND 和 OR

查询不可能只查询一个字段是否匹配,还有多个字段匹配的,所以就有像关系型数据库那样的ANDOR

AND 就是多个字段匹配,比如SQL语句中

where 列名1 = 值1 AND 列名2 = 值2

例子:

> db.col.find({title:"教育",name:"网易"})  //在第一个匹配的后面隔一个逗号就可以写下一个匹配的字段
{ "_id" : ObjectId("5d0346819cd49366b7f099ee"), "title" : "教育", "name" : "网易" }

OR 只需前面符合条件 后面符合条件,比如SQL语句中

where 列名1 = 值1 OR 列名2 = 值2

语法
db.collection.find({$or:[{字段名1:value1},{字段名2:value2}]})
主要是 $or 关键字

例子:

> db.col.find({$or:[{title:"教育"},{title:"人民教师"}]})
{ "_id" : ObjectId("5d0346819cd49366b7f099ee"), "title" : "教育", "name" : "网易" }
{ "_id" : ObjectId("5d0346819cd49366b7f099ef"), "title" : "人民教师", "name" : "腾讯" }

(2) $in, $nin范围查找

下一篇博客有讲条件操作符,>,<等,这里就不写了,这主要写 $in 关键字的用法,和SQL语句中的in 功能是一样的
当然肯定也相反的,比如 $nin,就是不再次范围内的

例子:

> db.mycol.find({grade:{$in:[85,90]}})
{ "_id" : ObjectId("5d05dc7ddfe22547ff8d6fd3"), "name" : "王宇", "grade" : 85 }
{ "_id" : ObjectId("5d05dc7ddfe22547ff8d6fd5"), "name" : "王芳", "grade" : 90 }

相反的 $nin就不演示了,和上面的格式一样,只是关键字变了

(3) 正则表达式(类似于JS的功能)

使用//或者使用$regex编写正则表达式

这里面详细说了关于MongoDB的正则表达式中的内容我就不再这写了,

(4) 自定义查询 $where

如查询成绩大于等于85的学生

> db.mycol.find({$where:function(){return this.grade>=85}})
{ "_id" : ObjectId("5d05dc7ddfe22547ff8d6fd3"), "name" : "王宇", "grade" : 85 }
{ "_id" : ObjectId("5d05dc7ddfe22547ff8d6fd5"), "name" : "王芳", "grade" : 90 }

上面的函数function 都是js函数,所以可以参考js函数来实现自定义查询

6、find({},{})映射指定列:(投影筛选) 两个参数

整个文档只显示某些字段

对于整个文档来说,自己需要的不一定就是文档的全部字段,而只需要某一个或多个字段,find()也可以实现

语法:

db.collection.find({},{字段名:1,_id:0})
//代表的是显示整个集合所有文档中有此字段名的显示出来,_id,必须加上,要不默认会显示,不显示冒号后为0
//对于冒号后面的数字0代表不显示,其他的数字代表显示
> db.col.find({},{title:1,_id:0})
{ "title" : "教育" }
{ "title" : "人民教师" }
{ "title" : "任教" }
{ "title" : 555 }

当然如果全部的字段都写出来,而且冒号后都是0, 解释就是都不显示,那就只显示 { } 了,有几条显示几条
还有一种情况,写出来的字段都为0还有没写出来的字段,那它就会把没显示出来的字段设置为显示

这样数据库,集合,文档的基本操作就结束了,还有很多方法需要自己去了解
一切都以MongoDB官网为主
MongoDB官网中对集合的文档操作的的方法

标签: