skip to Main Content

I’m new to MongoDB, so I may have some terminology wrong, but I don’t think I’ve seen anyone ask a question exactly like this:

If I have a collection of documents that have a shape something like:

{
_id: ObjectID('656ce741b78f8f5fea229c4f'),
year: 2,
name: "Student Name",
grades: [
  {
    date: ISODate('2014-08-16T00:00:00.000Z'),
    grade: 'A',
    score: 97
  },
  {
    date: ISODate('2014-03-19T00:00:00.000Z'),
    grade: 'A',
    score: 91
  },
  {
    date: ISODate('2015-08-16T00:00:00.000Z'),
    grade: 'B',
    score: 82
  }
]
}

How would I find all of the straight A students? That is, all of the students such that the grades array only contains grades.grade = "A". I can provide the actual document structure, but the logic should be the same for this example collection of imaginary student documents.

I’ve tried using $all, but I think that expects an array of values, not an array of objects. I’ve also tried $elemMatch with $ne: B and $ne: C, but that seems to return anything where at least one of the elements is an A, instead of requiring all elements to be A.

2

Answers


  1. The following query should only match documents where all elements of the grades array have a value that is not equal B or C:

    {"grades.grade":{$nin: ["C","B"]}}

    Login or Signup to reply.
  2. Instead of enumerating all the negative possibilities (i.e.the values that you don’t want, currently B and C), you can use $map to create a boolean array that check for grades.grade equal to A or not. Then, use $allElementsTrue on the resulting array to check whether all array entries are A or not. In this way, if you are introducing new negative values like D or E…, you code is still working as expected.

    db.collection.find({
      "$expr": {
        "$allElementsTrue": {
          "$map": {
            "input": "$grades",
            "as": "g",
            "in": {
              "$eq": [
                "$$g.grade",
                "A"
              ]
            }
          }
        }
      }
    })
    

    Mongo Playground

    Login or Signup to reply.
Please signup or login to give your own answer.
Back To Top
Search