首页 / MongoDB 入门教程 / 更新运算符总览

MongoDB 入门教程

更新运算符总览

本教程共 50 篇 · 第 22 篇 · 更新于 2026-07-30 · 约 8 分钟阅读

MongoDBMongoDB 入门教程更新运算符setincrename

22. 更新运算符总览

本节目标:掌握 MongoDB 的字段级更新运算符,知道用 $set 改值、$inc 做计数、$rename 改名等,写更新时不再只会整文档替换。

先记住一个关键点:更新文档(update 的第二参数)必须以更新运算符开头,比如 { $set: { ... } }。如果你写成 { price: 100 }(没有运算符),MongoDB 会把整篇文档替换掉——这往往不是你想要的。本章先逐个认识运算符,下一章再讲 updateOne/updateMany 这些调用方法。

db.products.insertMany([
  { _id: 101, name: "机械键盘", price: 399, stock: 50, tags: ["热销"], updated_at: null },
  { _id: 102, name: "无线鼠标", price: 129, stock: 120, tags: ["无线"], updated_at: null },
  { _id: 103, name: "27寸显示器", price: 1099, stock: 30, tags: ["4K"], updated_at: null }
])

$set:设置字段值

最常用的运算符,给字段赋值。字段不存在就新建:

// 把机械键盘价格改成 359,并新增一个 discount 字段
db.products.updateOne(
  { _id: 101 },
  { $set: { price: 359, discount: 0.9 } }
)

也能用点号改内嵌字段:

db.products.updateOne(
  { _id: 101 },
  { $set: { "location.type": "Point" } }
)

$unset:删除字段

把字段整个删掉,值为空即可:

// 删掉机械键盘的 discount 字段
db.products.updateOne(
  { _id: 101 },
  { $unset: { discount: "" } }
)
Note

$unset 的赋值写什么都行,MongoDB 只看键名。习惯上写空串 ""

$inc:按量增减

对数字字段做加法(负数即减法),非常适合计数器。字段不存在会从 0 开始加:

// 机械键盘库存减 5
db.products.updateOne(
  { _id: 101 },
  { $inc: { stock: -5 } }
)
Tip

库存扣减、点赞数 +1,这类「读旧值再写新值」的操作一定要用 $inc,别先查出来再 $set,否则并发时会算错。

$min 与 $max:只在更优时更新

$min 只在「新值比旧值小」时才写入;$max 反之,只在「新值比旧值大」时才写入:

// 只有新价格比当前低才降价
db.products.updateOne(
  { _id: 103 },
  { $min: { price: 999 } }
)
// 只有新库存比当前高才提高
db.products.updateOne(
  { _id: 102 },
  { $max: { stock: 150 } }
)

这俩运算符自带「条件判断」,不用先查再比。

$mul:乘法

把字段乘以某个数:

// 机械键盘价格打 8 折
db.products.updateOne(
  { _id: 101 },
  { $mul: { price: 0.8 } }
)

$rename:字段改名

把字段改名,旧名消失、新名出现:

// 把 stock 改名为 inventory
db.products.updateOne(
  { _id: 101 },
  { $rename: { stock: "inventory" } }
)
Warning

$rename 可以把字段移进或移出内嵌文档(比如从顶层改到 location.x)。但两个坑要记牢:目标字段若已存在会被直接覆盖;字段位于数组内时 $rename 用不了。改名前先确认目标字段不存在。

$currentDate:写入当前时间

自动写入服务器当前时间,适合「最后修改时间」:

// 把 updated_at 设为当前时间
db.products.updateOne(
  { _id: 101 },
  { $currentDate: { updated_at: true } }
)

想要时间戳(毫秒数)而非日期对象,就传 { $type: "timestamp" }

运算符一览

运算符作用典型场景
$set赋值/新建字段改任意字段值
$unset删除字段清理废弃字段
$inc增减数字库存、计数
$min/$max取更小/更大才写价格下限、分数上限
$mul乘法比例缩放
$rename改名字段重构
$currentDate写当前时间最后修改时间
Tip

一次更新可以组合多个运算符,它们会按顺序作用于同一篇文档:
{ $set: { price: 359 }, $inc: { stock: -1 }, $currentDate: { updated_at: true } }

运算符记熟了,下一章我们看清它们的「载具」:updateOneupdateManyreplaceOne