2

I am trying to find the minimum distance between arrays of numbers using a MongoDB query. My tech stack is Node.js+Mongoose with MongoDB 4.

Here's our input array, A:

A = [1, 2, 3, 4, 5]

And stored within MongoDB, we have objects like this:

[
  {
    id: 0
    nums: [4, 5, 6, 7, 8]
  },
  {
    id: 1
    nums: [-500, 50.2, 60, 74, 1]
  },
  {
    id: 2
    nums: [9, 5, 32, -7, 5]
  }
]

What I'm trying to do is sort the objects using the euclidian distance formula. For example, if we wanted to compare array A with id:0 in Mongo, I want to apply the Euclidean distance formula:

distance = Math.sqrt((a1-b1)^2 + (a2-b2)^2 + ... + (an-bn)^2)

In our case:

x = Math.sqrt((1-4)^2 + (2-5)^2 + (3-6)^2 + (4-7)^2 + (5-8)^2)

I want to find x for every array in the database, then sort by the minimum x value. In other words, I want to find the array that is most similar to our input.

I have some written basic queries in MongoDB before, but I'm really not sure how to approach this type of problem. Any help would be greatly appreciated.

1 Answer 1

2

You can start with $zip to "pair" your input array with nums. Then you can run $reduce to calculate Euclidean formula:

db.collection.aggregate([
    {
        $addFields: {
            distance: {
                $let: {
                    vars: {
                        pow: {
                            $reduce: {
                                input: { $zip: { inputs: [ [1, 2, 3, 4, 5], "$nums" ] } },
                                initialValue: 0,
                                in: {
                                    $add: [ 
                                        "$$value", 
                                        { $pow: [ 
                                            { $subtract: [ { $arrayElemAt: [ "$$this", 0 ] }, { $arrayElemAt: [ "$$this", 1 ] } ] } , 2 ] } 
                                        ]
                                }
                            }
                        }
                    },
                    in: { $sqrt: "$$pow" }
                }
            }
        }
    },
    {
        $sort: { distance: 1 }
    }
])

Mongo Playground

Sign up to request clarification or add additional context in comments.

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.