On this page
$ (update)
On this page
Definition
$
-
The positional
$
operator identifies an element in an array to update without explicitly specifying the position of the element in the array.Disambiguation
- To project, or return, an array element from a read operation, see the
$
projection operator instead. - To update all elements in an array, see the all positional operator
$[]
instead. - To update all elements that match an array filter condition or conditions, see the filtered positional operator instead
$[<identifier>]
.
The positional
$
operator has the form:{ "<array>.$" : value }
When used with update operations, e.g.
db.collection.update()
anddb.collection.findAndModify()
,- the positional
$
operator acts as a placeholder for the first element that matches thequery document
, and - the
array
field must appear as part of thequery document
.
For example:
db.collection.update( { <array>: value ... }, { <update operator>: { "<array>.$" : value } } )
- To project, or return, an array element from a read operation, see the
Behavior
upsert
Do not use the positional operator $
with upsert operations because inserts will use the $
as a field name in the inserted document.
Nested Arrays
The positional $
operator cannot be used for queries which traverse more than one array, such as queries that traverse arrays nested within other arrays, because the replacement for the $
placeholder is a single value
Unsets
When used with the $unset
operator, the positional $
operator does not remove the matching element from the array but rather sets it to null
.
Negations
If the query matches the array using a negation operator, such as $ne
, $not
, or $nin
, then you cannot use the positional operator to update values from this array.
However, if the negated portion of the query is inside of an $elemMatch
expression, then you can use the positional operator to update this field.
Examples
Update Values in an Array
Create a collection students
with the following documents:
db.students.insert([
{ "_id" : 1, "grades" : [ 85, 80, 80 ] },
{ "_id" : 2, "grades" : [ 88, 90, 92 ] },
{ "_id" : 3, "grades" : [ 85, 100, 90 ] }
])
To update the first element whose value is 80
to 82
in the in the grades
array, use the positional $
operator if you do not know the position of the element in the array:
Important
You must include the array field as part of the query
document.
db.students.updateOne(
{ _id: 1, grades: 80 },
{ $set: { "grades.$" : 82 } }
)
The positional $
operator acts as a placeholder for the first match of the update query document.
After the operation, the students
collection contains the following documents:
{ "_id" : 1, "grades" : [ 85, 82, 80 ] }
{ "_id" : 2, "grades" : [ 88, 90, 92 ] }
{ "_id" : 3, "grades" : [ 85, 100, 90 ] }
Update Documents in an Array
The positional $
operator facilitates updates to arrays that contain embedded documents. Use the positional $
operator to access the fields in the embedded documents with the dot notation on the $
operator.
db.collection.update(
{ <query selector> },
{ <update operator>: { "array.$.field" : value } }
)
Consider the following document in the students
collection whose grades
element value is an array of embedded documents:
{
_id: 4,
grades: [
{ grade: 80, mean: 75, std: 8 },
{ grade: 85, mean: 90, std: 5 },
{ grade: 85, mean: 85, std: 8 }
]
}
Use the positional $
operator to update the std
field of the first array element that matches the grade
equal to 85
condition:
Important
You must include the array field as part of the query
document.
db.students.updateOne(
{ _id: 4, "grades.grade": 85 },
{ $set: { "grades.$.std" : 6 } }
)
After the operation, the document has the following updated values:
{
"_id" : 4,
"grades" : [
{ "grade" : 80, "mean" : 75, "std" : 8 },
{ "grade" : 85, "mean" : 90, "std" : 6 },
{ "grade" : 85, "mean" : 85, "std" : 8 }
]
}
Update Embedded Documents Using Multiple Field Matches
The $
operator can update the first array element that matches multiple query criteria specified with the $elemMatch()
operator.
Consider the following document in the students
collection whose grades
field value is an array of embedded documents:
{
_id: 5,
grades: [
{ grade: 80, mean: 75, std: 8 },
{ grade: 85, mean: 90, std: 5 },
{ grade: 90, mean: 85, std: 3 }
]
}
In the example below, the $
operator updates the value of the std
field in the first embedded document that has grade
field with a value less than or equal to 90
and a mean
field with a value greater than 80
:
db.students.updateOne(
{
_id: 5,
grades: { $elemMatch: { grade: { $lte: 90 }, mean: { $gt: 80 } } }
},
{ $set: { "grades.$.std" : 6 } }
)
This operation updates the first embedded document that matches the criteria, namely the second embedded document in the array:
{
_id: 5,
grades: [
{ grade: 80, mean: 75, std: 8 },
{ grade: 85, mean: 90, std: 6 },
{ grade: 90, mean: 85, std: 3 }
]
}
See also