NoSQL学习之路(五):更新操作符
(UpdateOperators).2nd
通常⽂档只会有⼀部分要更新。利⽤原⼦的更新修改器,可以使得这种部分更新极为髙效。更新修改器是种特殊的键,⽤来指定复杂的更新操作,⽐如调整、增加或者删除键,还可能是操作数组或者内嵌⽂档。
字段更新操作符 Field Update Operators
$set
"$set"⽤来指定⼀个键的值。如果这个键不存在,则创建它。
我们往下⾯的⼀条⽤户资料添加“兴趣”信息,
db.users.insert({"name":"egger", "age": 28, "sex" : "male"})
运⾏下⾯的代码,将该⽤户的兴趣设置为“读书”并添加⾄⽂档中(此时⽂档中“hobby”键是不存在,该条⽂档就会创建它):
db.users.update({"_id" : ObjectId("51826852c75fdd1d8b805801")},
  {"$set" : {"hobby" :"read"}} )
当想更改⽤户的兴趣资料时,使⽤"$set" 然后将要更新的内容作为键“hobby”的值(下⾯的⽰例中将数组作为键值):
db.users.update({"_id" : ObjectId("51826852c75fdd1d8b805801")},
{"$set" : {"hobby" :["swimming","basketball"]}} )
⽤"$set"甚⾄可以修改键的数据类型
db.users.update({"_id" : ObjectId("51826852c75fdd1d8b805801")},{"$set" : {"sex" :1 }} )
执⾏结果如下:
使⽤"$set"修改内嵌⽂档:
该⽂档中的作者信息为内嵌⽂档,我们将其内容全部更改:
db.posts.update({"author.name":"egger"},{"$set":{"author.name":"mongo","author.age":18}})
$unset
从⽂档中移除指定的键。
若要完全删除键“hobby”,使⽤“$unset”即可:
db.users.update({"_id" : ObjectId("51826852c75fdd1d8b805801")},{"$unset" : {"hobby" :1 }} )
$inc
"$inc"修改器⽤来增加已有键的值,或者在键不存在时创建⼀个键。$inc就是专门来增加(和减少)数字的。"$inc"只能⽤于整数、长整数或双精度浮点数。要是⽤在其他类型的数据上就会导致操作失败。
例如毎次有⼈访问该博⽂,该条博⽂的浏览数就加1,⽤键"pageviews"保存浏览数信息。
下⾯使⽤"$inc”修改器增加"pageviews"的值
db.posts.update({"_id" : ObjectId("5180f1a991c22a72028238e4")}, {"$inc":{"pageviews":1}})
上⾯执⾏update时如果将键值设置为n,那么就表⽰该键的值增加n(n可以为负数)。
db.posts.update({"_id" : ObjectId("5180f1a991c22a72028238e4")}, {"$inc":{"pageviews":-100}})
$rename
语法: {$rename: { <old name1>: <new name1>, <old name2>: <new name2>, ... } }
$rename操作符可以重命名字段名称,新的字段名称不能和⽂档中现有的字段名相同。
如果⽂档中存在A、B字段,将B字段重命名为A,$rename会将A字段和值移除掉,然后将B字段名改为A.
集合students中的⼀条⽂档数据:
{ "_id": 1,
"nickname": [ "The American Cincinnatus", "The American Fabius" ],
"cell": "555-555-5555",
"name": { "first" : "george", "last" : "washington" }
}
将集合中"nickname"字段名重命名为“alias”、"cell"字段名重命名为"mobile":
db.students.update( { _id: 1 }, { $rename: { 'nickname': 'alias', 'cell': 'mobile' } } )
执⾏下⾯的更新操作,集合中已存在name字段,将会删除“name”字段,将“alias”字段名重命名为“name”db.students.update( { _id: 1 }, { $rename: { "alias": "name" } } )
当重命名⼦⽂档字段名时需要使⽤"."操作符,格式:值为该⼦⽂档的字段名.⼦⽂档中字段名。
db.students.update( { _id: 1 }, { $rename: { "name.first": "name.fname" } } )
执⾏上⾯的更新操作将name字段的值中first字段重命名为fname.
$rename操作符也可以将⼦⽂档中键值移到其他⼦⽂档中。
db.students.update( { _id: 1 }, { $rename: { "name.last": "contact.lname" } } )
我们将名为name的⼦⽂档中的last字段,重名为“lname”,同时将其移动到⼦⽂档contact中,若contact字段不存在,数据库会新建该字段。
若指定的字段在集合中不存在,$rename操作符将不会有任何影响。
db.students.update( { _id: 1 }, { $rename: { 'wife': 'spouse' } } )
若指定的多个字段在集合中都不存在,$rename操作符将不会有任何影响。
db.students.update( { _id: 1 }, { $rename: { 'wife': 'spouse', 'vice': 'vp',  'office': 'term' } } )
集合中不存在上⾯语句中指定的wife、vice、office字段,所以上述的更新操作⽆任何影响。
若指定的多个字段中,有的在集合中存在,有的不存在,$rename操作符执⾏下列操作:
存在的字段按照上⾯的规则重命名为新的名称。
不存在的字段对数据⽆任何影响。
db.students.update( { _id: 1 }, { $rename: { 'wife': 'alias', 'mobile': 'cell' } } )
执⾏上述更新操作,⽂档中只有“mobile”字段被替换为“cell”。
upsert
upsert是⼀种特殊的更新操作,不是⼀个操作符。(upsert = up[date]+[in]sert)
update() ⽅法的三个参数是upsert,这个参数是个布尔类型,默认是false。当它为true的时候,update⽅法会⾸先查与第⼀个参数匹配的记录,在⽤第⼆个参数更新之,如果不到与第⼀个参数匹配的的记录,就会以这个条件和更新⽂档为基础创建⼀个新的⽂档。如果到了匹配的⽂档,则正常更新。upsert⾮常⽅便,不必预置集合,同⼀套代码可以既创建⼜更新⽂档。
ve()
db.users.update({age :25}, {$inc :{"age" :3}}, true)
db.users.findOne()
我们将users集合清空,执⾏upsert操作,查询出age字段值为25的⽂档,然后将该字段值增加3.
由于我们先清空了集合,所以update操作将执⾏insert操作,先创建⼀个键“age”的值为25的⽂档,然后在将这个值增加3,即
键“age”的值为28,如图所⽰.
$setOnInsert
当update⽅法使⽤upsert选项执⾏insert操作时,$setOnInsert操作符给相应的字段赋值。类似sql中update 语句的set。
{ $setOnInsert: { <field1>: <value1>, ... } },
{ upsert: true }  //{ upsert: true }可以⽤true替换sql中update什么意思
)

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。