MongoDB常用命令
数据库与集合操作
(一)数据库操作
查看所有数据库
show dbs # 仅显示包含数据的库
切换 / 创建数据库若数据库不存在,插入数据时会自动创建:
use vlog # 切换到vlog库(不存在则隐含创建)
删除当前数据库
db.dropDatabase() # 谨慎操作!会删除当前库所有数据
(二)集合操作
创建集合可指定选项(如是否固定大小、最大文档数):
# 基本创建 db.createCollection("users") # 创建固定大小集合(适用于日志存储) db.createCollection("system_logs", { capped: true, size: 1048576, # 集合最大字节数(1MB) max: 1000 # 最大文档数 })
查看当前库集合
show collections
删除集合
db.users.drop() # 删除users集合
数据插入命令
(一)单条数据插入
使用insertOne
命令,我们可以轻松地将一个文档插入到指定的集合中。它的语法格式为:
db.users.insertOne(
<document>,
{
writeConcern: <document>,
bypassDocumentValidation: <boolean>
}
)
document
:这是要插入的文档,它是一个类似 JSON 的结构,包含了各种字段和对应的值。例如{ "name": "张三", "age": 25, "city": "北京" }
,就定义了一个人的基本信息文档。
writeConcern
(可选):用于指定写入操作的确认级别,它控制了 MongoDB 在返回结果给客户端之前,需要等待多少个副本集成员确认写入操作。比如{ "w": "majority", "wtimeout": 5000 }
,表示等待大多数副本集成员确认写入,并且设置超时时间为 5000 毫秒。如果在这个时间内没有得到大多数成员的确认,操作将失败并返回错误。
bypassDocumentValidation
(可选):一个布尔值,默认值为false
。当设置为true
时,会绕过集合的文档验证规则,直接插入文档。一般情况下,我们不建议随意绕过验证,因为文档验证规则可以确保插入的数据符合一定的格式和约束,有助于保证数据的质量和一致性。
(二)批量数据插入
当我们需要一次性插入多条数据时,使用批量插入命令可以大大提高效率,减少与数据库的交互次数,就如同一次搬运多本书到书架上。MongoDB 提供了insertMany
命令来实现批量插入操作。其语法如下:
db.collection.insertMany(
[ <document 1>, <document 2>,... ],
{
writeConcern: <document>,
ordered: <boolean>,
bypassDocumentValidation: <boolean>
}
)
[ <document 1>, <document 2>,... ]
:这是一个包含多个文档的数组,每个文档都是要插入到集合中的数据。例如[ { "name": "王五", "age": 28, "city": "上海" }, { "name": "赵六", "age": 35, "city": "广州" } ]
,定义了两个要插入的文档。
writeConcern
(可选):与insertOne
中的writeConcern
含义相同,用于指定写入操作的确认级别。
ordered
(可选):一个布尔值,默认值为true
。当设置为true
时,插入操作会按照文档数组的顺序依次进行,一旦某个文档插入失败,后续的文档将不再插入;当设置为false
时,插入操作是无序的,即使某个文档插入失败,其他文档仍会继续插入,并且会在结果中返回每个文档插入的状态。
bypassDocumentValidation
(可选):同样是一个布尔值,默认值为false
,用于控制是否绕过文档验证规则。
数据查询命令
mongoDB中使用find
命令实现数据查询
db.users.find(<查询条件>,<投影规则>)
(一)简单查询
在 MongoDB 中,简单查询是最基本的数据查询操作,就像在图书馆中查找所有书籍一样。通过简单查询,我们可以获取集合中的所有文档,或者根据特定条件筛选出部分文档。
查询集合中的所有文档是一种常见的操作,它能让我们快速浏览集合中的全部数据。在 MongoDB 中,使用find
命令可以轻松实现这一功能。例如,我们有一个名为users
的集合,要查询其中的所有用户信息,可以执行以下命令:
db.users.find()
这条命令会返回users
集合中的所有文档。不过,默认情况下,MongoDB 返回的结果可能不太美观,难以阅读。为了让结果更具可读性,我们可以使用pretty
方法对结果进行格式化输出。示例如下:
db.users.find().pretty()
pretty
方法会将查询结果以缩进的、更易读的格式展示出来,方便我们查看文档的结构和内容。
如果我们只需要返回集合中的第一条文档,可以使用findOne
命令。比如,要获取users
集合中的第一个用户信息,命令如下:
db.users.findOne()
findOne
方法会返回满足查询条件的第一个文档,如果没有指定条件,就返回集合中的第一条文档。它与find
方法的区别在于,find
返回的是一个游标,可以遍历多个文档,而findOne
直接返回一个文档对象。在某些场景下,当我们只关心集合中的某一个特定文档(如第一条文档)时,findOne
能更高效地获取所需数据 。
(二)条件查询
条件查询是 MongoDB 查询功能的核心部分,它允许我们根据各种条件筛选出符合要求的文档,就如同在图书馆中根据书名、作者等条件查找特定的书籍。MongoDB 提供了丰富的条件运算符,包括比较运算符、逻辑运算符、范围运算符、正则表达式等,让我们能够灵活地构建各种复杂的查询条件。
比较运算符用于比较字段值与指定值的关系,常见的比较运算符有:
$eq
:等于,例如{ "age": { "$eq": 30 } }
,表示查询年龄等于 30 的文档,也可以简写成{ "age": 30 }
。
$ne
:不等于,如{ "age": { "$ne": 30 } }
,表示查询年龄不等于 30 的文档。
$gt
:大于,{ "age": { "$gt": 30 } }
,查询年龄大于 30 的文档。
$gte
:大于等于,{ "age": { "$gte": 30 } }
,查询年龄大于等于 30 的文档。
$lt
:小于,{ "age": { "$lt": 30 } }
,查询年龄小于 30 的文档。
$lte
:小于等于,{ "age": { "$lte": 30 } }
,查询年龄小于等于 30 的文档。
逻辑运算符用于组合多个条件,实现更复杂的查询逻辑。主要的逻辑运算符有:
$and
:逻辑与,用于连接多个条件,只有当所有条件都满足时,文档才会被返回。例如{ "$and": [ { "age": { "$gt": 30 } }, { "city": "北京" } ] }
,表示查询年龄大于 30 且城市为北京的文档,也可以直接写成{ "age": { "$gt": 30 }, "city": "北京" }
。
$or
:逻辑或,连接多个条件,只要其中一个条件满足,文档就会被返回。如{ "$or": [ { "age": 30 }, { "city": "上海" } ] }
,表示查询年龄为 30 或者城市为上海的文档。
范围运算符可以用来查询某个字段值在指定范围内的文档。例如,我们要查询年龄在 20 到 30 岁之间(包括 20 和 30)的用户,可以使用$gte
和$lte
运算符组合:
db.users.find({ "age": { "$gte": 20, "$lte": 30 } })
正则表达式在条件查询中也非常有用,它可以用于模糊匹配字符串。比如,我们要查询所有名字以 “张” 开头的用户,可以使用$regex
运算符结合正则表达式:
db.users.find({ "name": { "$regex": "^张" } })
这里的^张
表示以 “张” 开头的字符串。
除了上述常用的查询方式,MongoDB 还支持自定义查询,通过$where
运算符可以使用 JavaScript 表达式进行查询。例如,查询年龄大于 20 且小于 30 的用户,可以这样写:
db.users.find({ "$where": "this.age > 20 && this.age < 30" })
不过,由于$where
使用 JavaScript 表达式进行查询,性能相对较低,在实际应用中应尽量避免使用,除非其他查询方式无法满足需求。
(三)查询指定字段
只返回指定字段(包含 _id
)
例如,查询所有用户,只返回 username
和 age
字段(默认包含 _id
):
db.users.find({}, { username: 1, age: 1 })
返回结果类似:
{ "_id": ObjectId("..."), "username": "zhangsan", "age": 28 }
{ "_id": ObjectId("..."), "username": "lisi", "age": 30 }
排除 _id
字段
若不需要默认返回的 _id
,需显式设置 _id: 0
:
db.users.find({}, { username: 1, age: 1, _id: 0 })
返回结果类似:
{ "username": "zhangsan", "age": 28 }
{ "username": "lisi", "age": 30 }
排除指定字段(返回其他所有字段)
例如,查询所有用户,排除 roles
和 createTime
字段(其他字段均返回,包括 _id
):
db.users.find({}, { roles: 0, createTime: 0 })
结合查询条件的投影
例如,查询年龄大于 25 的用户,只返回 username
和 roles
:
db.users.find(
{ age: { $gt: 25 } }, // 查询条件:年龄>25
{ username: 1, roles: 1, _id: 0 } // 只返回这两个字段
)
(四)分页与排序
在实际应用中,当集合中的数据量较大时,我们可能并不需要一次性获取所有数据,而是希望对查询结果进行分页显示,同时还可能需要对结果进行排序,以便更好地展示和处理数据。就像在图书馆中,如果书籍众多,我们可能会希望按类别排序,并分页查看。
在 MongoDB 中,使用limit
命令可以限制返回的文档数量,实现分页功能中的 “每页显示数量”。例如,要获取users
集合中的前 10 条文档,可以执行以下命令:
db.users.find().limit(10)
skip
命令则用于跳过指定数量的文档,实现分页功能中的 “偏移量”。比如,要获取users
集合中第 11 到第 20 条文档(即跳过前 10 条文档),可以这样写:
db.users.find().skip(10).limit(10)
sort
命令用于对查询结果进行排序。它接受一个文档参数,其中字段名表示要排序的字段,值为 1 表示升序排序,值为 -1 表示降序排序。例如,要按照用户的年龄升序排列,可以执行:
db.users.find().sort({ "age": 1 })
如果要按照年龄降序排列,并且当年龄相同时按照姓名升序排列,可以这样写:
db.users.find().sort({ "age": -1, "name": 1 })
数据更新命令
(一)基本更新
在 MongoDB 中,数据更新是一项非常重要的操作,它允许我们修改已存储在集合中的文档数据。就像在图书馆中,我们可能需要修改某本书的信息一样,MongoDB 提供了多种更新命令来满足不同的需求。
updateOne
命令用于更新集合中符合条件的第一条文档,它是一个原子操作,确保在并发环境下数据的一致性。其语法格式如下:
db.collection.updateOne(
<filter>,
<update>,
{
upsert: <boolean>,
writeConcern: <document>,
bypassDocumentValidation: <boolean>
}
)
<filter>
:这是一个查询条件,用于筛选出要更新的文档。例如{ "name": "张三" }
,表示筛选出名字为 “张三” 的文档。
<update>
:定义了要执行的更新操作,通常使用更新操作符来指定具体的更新内容。比如{ $set: { "age": 30 } }
,表示将文档中的age
字段设置为 30。
upsert
(可选):一个布尔值,默认值为false
。当设置为true
时,如果没有找到符合条件的文档,会插入一个新的文档。例如,我们希望更新名字为 “李四” 的用户年龄,如果没有找到 “李四” 的文档,并且upsert
设置为true
,则会插入一个新的文档,内容为{ "name": "李四", "age": 新设置的年龄 }
。
writeConcern
(可选):与插入命令中的writeConcern
类似,用于指定写入操作的确认级别。
bypassDocumentValidation
(可选):控制是否绕过文档验证规则,默认值为false
。
(二)更新操作符
MongoDB 提供了丰富的更新操作符,这些操作符使得我们能够进行各种复杂的数据更新操作,极大地增强了更新功能的灵活性和实用性。
$set
:用于设置字段的值,如果字段不存在则创建该字段。例如,我们要将名字为 “赵六” 的用户的email
字段设置为 “zhaoliu@example.com”,可以使用以下命令:
db.users.updateOne({ "name": "赵六" }, { $set: { "email": "zhaoliu@example.com" } })
$unset
:用于删除指定的字段。比如,要删除名字为 “孙七” 的用户的city
字段,命令如下:
db.users.updateOne({ "name": "孙七" }, { $unset: { "city": "" } })
这里$unset
后面的值可以是任意非空值,通常使用空字符串或 1。在 Java 中:
$inc
:用于对数值类型的字段进行增加或减少操作。如果字段不存在,则会创建该字段并初始化为指定的增量值。例如,要将所有用户的score
字段增加 10 分,可以使用:
db.users.updateMany({}, { $inc: { "score": 10 } })
$push
:用于向数组类型的字段中添加一个元素。如果字段不存在,会创建一个包含该元素的新数组。例如,用户文档中有一个hobbies
数组字段,要为名字为 “周八” 的用户添加一个 “跑步” 的爱好,可以这样做:
db.users.updateOne({ "name": "周八" }, { $push: { "hobbies": "跑步" } })
$pull
:从数组类型的字段中删除指定的元素。比如,要从名字为 “吴九” 的用户的hobbies
数组中删除 “游泳” 这个爱好,命令如下:
db.users.updateOne({ "name": "吴九" }, { $pull: { "hobbies": "游泳" } })
$addToSet
:向数组中添加一个元素,但前提是该元素在数组中不存在,用于确保数组中元素的唯一性。例如,要为名字为 “郑十” 的用户添加一个 “阅读” 的爱好,且保证 “阅读” 不会重复添加,可以使用:
db.users.updateOne({ "name": "郑十" }, { $addToSet: { "hobbies": "阅读" } })
$rename
:用于重命名字段。比如,将用户文档中的phone_number
字段重命名为mobile
,可以执行:
db.users.updateMany({}, { $rename: { "phone\_number": "mobile" } })
$mul
:用于对数值类型的字段进行乘法运算。例如,将所有用户的price
字段乘以 2,可以使用:
db.users.updateMany({}, { $mul: { "price": 2 } })
(三)批量更新
当我们需要一次性更新多个文档时,updateMany
命令就派上用场了。它可以根据指定的条件,批量更新集合中的多个文档,大大提高了数据更新的效率。其语法格式为:
db.collection.updateMany(
<filter>,
<update>,
{
upsert: <boolean>,
writeConcern: <document>,
bypassDocumentValidation: <boolean>
}
)
<filter>
、<update>
、upsert
、writeConcern
和bypassDocumentValidation
的含义与updateOne
命令中的相同。
例如,在一个电商系统中,我们有一个名为products
的集合,存储了商品的信息。现在要将所有库存数量小于 10 的商品的状态更新为 “缺货”,可以使用以下命令:
db.products.updateMany(
{ "stock": { "$lt": 10 } },
{ $set: { "status": "缺货" } }
)
数据删除命令
(一)单条数据删除
官方推荐使用deleteOne
命令来删除符合条件的单个文档。其语法格式如下:
db.collection.deleteOne(
<filter>,
{
writeConcern: <document>,
collation: <document>
}
)
<filter>
:这是一个查询条件,用于筛选出要删除的文档,类似于 SQL 中的WHERE
子句。例如{ "name": "张三" }
,表示筛选出名字为 “张三” 的文档进行删除。
writeConcern
(可选):用于指定写入操作的确认级别,它控制了 MongoDB 在返回结果给客户端之前,需要等待多少个副本集成员确认删除操作。比如{ "w": "majority", "wtimeout": 5000 }
,表示等待大多数副本集成员确认删除,并且设置超时时间为 5000 毫秒。如果在这个时间内没有得到大多数成员的确认,操作将失败并返回错误。
collation
(可选):指定排序规则,用于在执行删除操作时对文档进行排序。例如{ locale: "en_US", strength: 2 }
,表示使用美国英语的排序规则,并且强度为 2,强度决定了排序时对字符差异的敏感度 。
(二)多条数据删除
当需要删除多条符合条件的数据时,deleteMany
命令就发挥了作用,它可以一次性删除多个文档,如同一次性从书架上拿走多本书。其语法格式为:
db.collection.deleteMany(
<filter>,
{
writeConcern: <document>,
collation: <document>
}
)
<filter>
、writeConcern
和collation
的含义与deleteOne
命令中的相同。
例如,在一个电商系统中,我们有一个名为orders
的集合,存储了订单信息。现在要删除所有状态为 “已取消” 的订单,可以使用以下命令:
db.orders.deleteMany({ "status": "已取消" })