问题
arr=[{field1:<value1>,field2:<value2}.....]
I want to use the $in
operator against the field1
of arr
. I know I could create a dummy array and push the field1
values in the dummy array. But is there a way to use the $in
operator against a particular field of an array?
The arr
array is no way related to the collection.
I want to query all the documents on a particular field whose value is in the field1
of arr
- field1 should be in the right hand side of operator $in
Example:
arr=[{name:'foo',location:'NY'},{name:'bar',location:'LA'},{name:'foobar',location:'NZ'}]
db.collection.find({fieldx:<Here I want some method to obtain all documents whose fieldx values are in the location field of arr>})
The output should contain documents whose fieldx
values are present in the location
field of arr
.
The ouput of the query should be
[{...
fieldx:'NY',
...
},
{...
fieldx:'LA',
...
},
{...
fieldx:'NZ',
...
}]
fieldx
is the field in the collection I am querying on. It is not a field of the array I'm providing(arr
). I want to match this to a field(location
) of array - arr
I'm providing the query.
回答1:
You need to extract the "location" fields from your input array and feed them to $in
:
var locs = arr.map(function(x) { return x.location } );
db.collection.find({ "fieldx": { "$in": locs } })
For reference here I'm going to re-write your question for you:
I have a collection that contains documents like this:
{ "fieldx": "NY" }
{ "fieldx": "LA" }
{ "fieldx": "SF" }
What I have is an input array that is defined like this:
var arr = [
{ "name": "foo", "location": "NY"},
{ "name": "bar", "location": "LA"},
{ "name": "foobar", "location": "NZ"}
];
Now I want to write a query to find all the documents that match the "location" field in the array I have for input.
How do I do I do that?
I have tried:
db.collection.find({ "fieldx": { "$in": arr } })
But that does not match.
回答2:
Extending Neil Lunn's answers, you can use map
function within query also.
var arr = [
{ "name": "foo", "location": "NY"},
{ "name": "bar", "location": "LA"},
{ "name": "foobar", "location": "NZ"}
];
db.collection.find({ "fieldx": { "$in": arr.map(function(x) { return x.location } ) } })
If you using ES6 syntax then
db.collection.find({ "fieldx": { "$in": arr.map(x => x.location ) } })
回答3:
You need to use dot notation to select fields in the array:
db.coll.find({"arr.field1" : { $in : [ 'value1', 'value11' ]}});
This query will return all documents where array arr
contains at least one subdocument that has a field field1
with values value1
or value11
.
Edit
Regarding your edit, you can't use $in operator that way.
From the documentation:
The $in operator selects the documents where the value of a field equals any value in the specified array.
If you send an array of objects in the $in query it will match document where specified field contains that object:
db.coll.find({ a: { $in : [ { b : 1, c: 1}, { b : 2, c: 2} ]}});
Will find this documents:
{
_id : ...
a: { b : 1, c: 1}
}
{
_id : ...
a: { b : 2, c: 2}
}
To get what you really want, easiest way to query is to extract the values from your array of objects and do a query with the created array of values.
来源:https://stackoverflow.com/questions/24503323/mongodb-in-against-a-field-of-objects-of-array-instead-of-objects-of-array