सबसे सरल अर्थ में यह मोंगोडीबी द्वारा उपयोग किए जाने वाले "डॉट नोटेशन" के मूल रूप का पालन करता है। यह इस बात पर ध्यान दिए बिना काम करेगा कि आंतरिक सरणी सदस्य किस सरणी सदस्य में है, जब तक यह किसी मान से मेल खाता है:
db.mycollection.find({
"someArray.someNestedArray.name": "value"
})
यह "एकल फ़ील्ड" मान के लिए ठीक है, एकाधिक-फ़ील्ड से मेल खाने के लिए आप $elemMatch
का उपयोग करेंगे :
db.mycollection.find({
"someArray": {
"$elemMatch": {
"name": "name1",
"someNestedArray": {
"$elemMatch": {
"name": "value",
"otherField": 1
}
}
}
}
})
यह उस दस्तावेज़ से मेल खाता है जिसमें उस "पथ" पर फ़ील्ड के साथ कुछ होगा जो मूल्य से मेल खाता है। यदि आप परिणाम को "मिलान और फ़िल्टर" करने का इरादा रखते हैं, तो केवल मिलान किए गए तत्व को वापस कर दिया गया था, यह स्थितीय ऑपरेटर प्रक्षेपण के साथ संभव नहीं है, जैसा कि उद्धृत किया गया है:
<ब्लॉकक्वॉट>नेस्टेड सरणी
स्थितीय $ ऑपरेटर का उपयोग उन प्रश्नों के लिए नहीं किया जा सकता है जो एक से अधिक सरणी को पार करते हैं, जैसे कि क्वेरी जो अन्य सरणियों के भीतर नेस्टेड सरणियों को पार करती हैं, क्योंकि $ प्लेसहोल्डर के लिए प्रतिस्थापन एक एकल मान है
आधुनिक MongoDB
हम $filter
. लागू करके ऐसा कर सकते हैं और $map
यहाँ। $map
वास्तव में आवश्यक है क्योंकि "आंतरिक" सरणी "फ़िल्टरिंग" के परिणामस्वरूप बदल सकती है, और निश्चित रूप से "बाहरी" सरणी उन स्थितियों से मेल नहीं खाती जब "आंतरिक" सभी तत्वों से छीन लिया गया था।
वास्तव में प्रत्येक सरणी के भीतर मिलान करने के लिए कई गुण होने के उदाहरण का अनुसरण करते हुए:
db.mycollection.aggregate([
{ "$match": {
"someArray": {
"$elemMatch": {
"name": "name1",
"someNestedArray": {
"$elemMatch": {
"name": "value",
"otherField": 1
}
}
}
}
}},
{ "$addFields": {
"someArray": {
"$filter": {
"input": {
"$map": {
"input": "$someArray",
"as": "sa",
"in": {
"name": "$$sa.name",
"someNestedArray": {
"$filter": {
"input": "$$sa.someNestedArray",
"as": "sn",
"cond": {
"$and": [
{ "$eq": [ "$$sn.name", "value" ] },
{ "$eq": [ "$$sn.otherField", 1 ] }
]
}
}
}
}
},
},
"as": "sa",
"cond": {
"$and": [
{ "$eq": [ "$$sa.name", "name1" ] },
{ "$gt": [ { "$size": "$$sa.someNestedArray" }, 0 ] }
]
}
}
}
}}
])
इसलिए "बाहरी" सरणी पर $filter
वास्तव में $size
. को देखता है "आंतरिक" सरणी के बाद इसे "फ़िल्टर" किया गया था, इसलिए आप उन परिणामों को अस्वीकार कर सकते हैं जब संपूर्ण आंतरिक सरणी वास्तव में नोटिंग से मेल खाती है।
पुराना MongoDB
केवल मिलान किए गए तत्व को "प्रोजेक्ट" करने के लिए, आपको .aggregate()
. की आवश्यकता होगी विधि:
db.mycollection.aggregate([
// Match possible documents
{ "$match": {
"someArray.someNestedArray.name": "value"
}},
// Unwind each array
{ "$unwind": "$someArray" },
{ "$unwind": "$someArray.someNestedArray" },
// Filter just the matching elements
{ "$match": {
"someArray.someNestedArray.name": "value"
}},
// Group to inner array
{ "$group": {
"_id": {
"_id": "$_id",
"name": "$someArray.name"
},
"someKey": { "$first": "$someKey" },
"someNestedArray": { "$push": "$someArray.someNestedArray" }
}},
// Group to outer array
{ "$group": {
"_id": "$_id._id",
"someKey": { "$first": "$someKey" },
"someArray": { "$push": {
"name": "$_id.name",
"someNestedArray": "$someNestedArray"
}}
}}
])
यह आपको दस्तावेज़ में एक या अधिक परिणामों के लिए नेस्टेड सरणियों में मिलानों को "फ़िल्टर" करने की अनुमति देता है।