Notera kommandot några rader ner i dokumentationen du länkade:
Detta talar om för dig att icke-existerande fält och fält inställda på null behandlas speciellt.
För dokumenten {}
och {a: null}
för att vara ekvivalent i sorteringsordning måste sorteringsalgoritmen överväga att det saknade sorteringsfältet finns och ha värdet null
.
Om du uttryckligen lägger till det saknade fältet, bara för att se hur det ser ut, är beställningen mer meningsfull.
Filtret {tag: { $gte: { baz: MinKey() }}}
tillämpas på {_id: 1, tag: {bar: "BAR"}}
jämför i huvudsak {baz: MinKey()}
med {baz: null, bar: "BAR"}
.
Nära toppen av dokumentationen du länkade står det att MinKey
är mindre än null
, så det är rätt ordning.
REDIGERA
I allmänhet är förfrågningar mest effektivt när fältnamnen inte själva är data. När det gäller en tabelldatabas, vilken kolumn skulle innehålla "baz"?
En liten förändring i schemat skulle förenkla denna typ av fråga. Istället för {tagname: tagvalue}
, använd {k:tagname, v:tagvalue}
. Du kan sedan indexera tag.k
och/eller tag.v
, och fråga på tag.k
för att hitta alla dokument med en "baz"-tagg skulle fråga efter taggar med ojämlikhetsoperationer fungera mer intuitivt.
db.collection.find({"tag.k":{$gte:"baz"}})
Exakta matchningar kan göras med elemMatch like
db.collection.find({tag: {$elemMatch:{k:"baz",v:"BAZ"}}})
Om du verkligen behöver att de returnerade dokumenten ska innehålla {tagname: tagvalue}
, $arrayToObject
aggregeringsoperatör kan göra det:
db.collection.aggregate([
{$match: {
"tag.k": {$gte: "baz"}
}},
{
$addFields: {
tag: {$arrayToObject: [["$tag"]]}
}}
])