MongoDB에서 배열 검색 후 인덱스를 새 배열로 출력하기
배열 안에서 다른 배열에 포함된 값을 검색하고, 찾은 값들의 인덱스를 새로운 배열로 출력하려면 $indexOfArray 연산자를 사용하면 됩니다. $indexOfArray는 지정한 배열에서 특정 값이 처음 나타나는 위치(인덱스)를 반환하며, 해당 값이 존재하지 않으면 -1을 반환한다는 점을 기억해 두면 좋습니다.
먼저 문서를 포함하는 컬렉션을 생성해 보겠습니다.
> db.demo381.insertOne({"Values":[10,40,60,30,60]});
{
"acknowledged" : true,
"insertedId" : ObjectId("5e5b59f72ae06a1609a00b15")
}
> db.demo381.insertOne({"Values":[100,500,700,500,800]});
{
"acknowledged" : true,
"insertedId" : ObjectId("5e5b59f72ae06a1609a00b16")
}
> db.demo381.insertOne({"Values":[20,40,30,10,60]});
{
"acknowledged" : true,
"insertedId" : ObjectId("5e5b59f72ae06a1609a00b17")
}컬렉션 문서 조회하기
find() 메서드를 사용하여 컬렉션의 모든 문서를 확인할 수 있습니다.
> db.demo381.find();
위 명령은 다음과 같은 결과를 출력합니다.
{ "_id" : ObjectId("5e5b59f72ae06a1609a00b15"), "Values" : [ 10, 40, 60, 30, 60 ] }
{ "_id" : ObjectId("5e5b59f72ae06a1609a00b16"), "Values" : [ 100, 500, 700, 500, 800 ] }
{ "_id" : ObjectId("5e5b59f72ae06a1609a00b17"), "Values" : [ 20, 40, 30, 10, 60 ] }$map과 $indexOfArray를 활용한 검색 쿼리
다음은 한 배열에서 다른 배열에 존재하는 값을 검색하고, 찾은 값의 인덱스를 새 배열로 출력하는 MongoDB 애그리게이션 쿼리입니다.
> db.demo381.aggregate([
... {"$project":{
... "Result":{
... "$map":{
... "input":[10,40],
... "in":{"$indexOfArray":["$Values","$$this"]}
... }
... }
... }}
... ])이 쿼리의 동작 원리는 다음과 같습니다. $map 연산자가 검색 대상 배열인 [10, 40]의 각 요소($$this)를 하나씩 순회하면서, 각 요소에 대해 $indexOfArray를 실행하여 Values 필드 배열 내에서 해당 값이 위치한 인덱스를 구합니다. 그 결과들이 모여 새로운 Result 배열이 생성됩니다.
위 쿼리는 다음과 같은 결과를 출력합니다.
{ "_id" : ObjectId("5e5b59f72ae06a1609a00b15"), "Result" : [ 0, 1 ] }
{ "_id" : ObjectId("5e5b59f72ae06a1609a00b16"), "Result" : [ -1, -1 ] }
{ "_id" : ObjectId("5e5b59f72ae06a1609a00b17"), "Result" : [ 3, 1 ] }결과 해석
출력된 결과를 문서별로 살펴보면 다음과 같습니다.
- 첫 번째 문서: Values 배열이 [10, 40, 60, 30, 60]이므로 10은 인덱스 0, 40은 인덱스 1에 위치합니다. 따라서 Result는 [0, 1]입니다.
- 두 번째 문서: Values 배열이 [100, 500, 700, 500, 800]으로 10과 40이 모두 존재하지 않습니다. 따라서 Result는 [-1, -1]입니다.
- 세 번째 문서: Values 배열이 [20, 40, 30, 10, 60]이므로 10은 인덱스 3, 40은 인덱스 1에 위치합니다. 따라서 Result는 [3, 1]입니다.
이처럼 $map과 $indexOfArray를 조합하면 여러 개의 검색 값을 한 번의 애그리게이션으로 처리하여, 각 값의 위치 정보를 손쉽게 새로운 배열 형태로 얻을 수 있습니다.