1
data: [
    {
            "_id" : ObjectId("5ebda923a52984db48ab45f6"),
            "detectorid" : 1371,
            "loopdata" : [
                    {
                            "starttime" : "9/15/2011 0:00:00",
                            "volume" : 2,
                            "speed" : 65,
                            "occupancy" : 2,
                            "status" : 2,
                            "dqflags" : 0
                    },
                    {
                            "starttime" : "9/15/2011 0:00:20",
                            "volume" : 2,
                            "speed" : 53,
                            "occupancy" : 2,
                            "status" : 2,
                            "dqflags" : 0
                    },
                    {
                            "starttime" : "9/15/2011 0:00:40",
                            "volume" : 0,
                            "speed" : "",
                            "occupancy" : 0,
                            "status" : 0,
                            "dqflags" : 0
                    }
]

Hey guys, this is the data that I have in my collection. I want to return back the speed is over 53. I have tried and db.collection.find({"data.speed":{$gt:53}})

it returned the wrong results (basically returned everything) and I have no idea what I wrong. Any hints guys? Thanks

prasad_
  • 12,755
  • 2
  • 24
  • 36
Kim Ma
  • 13
  • 2
  • Does this answer your question? [How to search in array of object in mongodb](https://stackoverflow.com/questions/14040562/how-to-search-in-array-of-object-in-mongodb). As given there you need to use `$gt` condition in `$elemMatch` – whoami - fakeFaceTrueSoul May 14 '20 at 21:37
  • I read that post, not working though – Kim Ma May 14 '20 at 21:51

1 Answers1

0

I made to you two solutions:

  1. If you just want to keep a speeds field and the _id document, this solve the problem:

Query:

db.collection.aggregate([
  // $filter will apply the condition to every element of the array
  // in this case the array is [65, 53 ""]
  {
    $project: {
      "speeds": {
        $filter: {
          "input": "$loopdata.speed",
          "as": "speed",
          "cond": {
            $and: [
              {
                $eq: [
                  {
                    $type: "$$speed" // check if the type is numeric
                  },
                  "double"
                ]
              },
              {
                $gt: [
                  "$$speed",  // check if it's greater than 53
                  53
                ]
              }
            ]
          }
        }
      }
    }
  }
])

Result:

[
  {
    "_id": ObjectId("5ebda923a52984db48ab45f6"),
    "speeds": [
      65
    ]
  }
]
  1. Now if you want to keep all the fields, and filter just the array loopdata, so this solves the problem:

Query 2:

db.collection.aggregate([
  {
    $addFields: {
      "loopdata": {
        $filter: {
          "input": "$loopdata",
          "as": "data",
          "cond": {
            $and: [
              {
                $eq: [
                  {
                    $type: "$$data.speed"
                  },
                  "double"
                ]
              },
              {
                $gt: [
                  "$$data.speed",
                  53
                ]
              }
            ]
          }
        }
      }
    }
  }
])

Result:

[
  {
    "_id": ObjectId("5ebda923a52984db48ab45f6"),
    "detectorid": 1371,
    "loopdata": [
      {
        "dqflags": 0,
        "occupancy": 2,
        "speed": 65,
        "starttime": "9/15/2011 0:00:00",
        "status": 2,
        "volume": 2
      }
    ]
  }
]
igorkf
  • 3,159
  • 2
  • 22
  • 31