복합 인덱스를 사용한 정렬
인덱스는 쿼리 속도 향상뿐만 아니라 효율적인 정렬에도 매우 중요합니다. 인덱스가 없는 필드로 정렬하면 MongoDB 는 메모리 내에서 정렬을 수행해야 하며, 이는 느리고 상당한 RAM 을 소비할 수 있습니다. 여러 필드를 포함하는 **복합 인덱스 (compound index)**는 해당 필드로 필터링하고 정렬하는 쿼리를 최적화할 수 있습니다.
city(오름차순) 및 age(내림차순) 필드에 복합 인덱스를 생성해 보겠습니다. 인덱스 내 필드의 순서는 인덱스가 사용되는 방식에 중요합니다.
db.users.createIndex({ city: 1, age: -1 });
이제 사용자를 도시별로, 그리고 나이별로 정렬하는 쿼리를 실행해 보겠습니다. 인덱스가 정렬에 사용되는지 확인하기 위해 다시 .explain()을 사용합니다.
db.users.find().sort({ city: 1, age: -1 }).explain("executionStats");
예시 출력 (일부 발췌):
{
"queryPlanner": {
"winningPlan": {
"stage": "FETCH",
"inputStage": {
"stage": "IXSCAN",
"keyPattern": { "city": 1, "age": -1 },
"indexName": "city_1_age_-1"
}
}
}
}
IXSCAN 단계는 MongoDB 가 새로운 city_1_age_-1 인덱스를 사용했음을 보여줍니다. 데이터가 인덱스에 이미 정렬 기준에 따라 정렬되어 있으므로 MongoDB 는 별도의 비용이 많이 드는 메모리 내 정렬 단계를 수행할 필요가 없습니다.
실제 정렬된 결과를 보려면 .explain() 없이 쿼리를 실행합니다.
db.users.find().sort({ city: 1, age: -1 });
출력:
[
{ _id: ObjectId("..."), name: 'Charlie', age: 42, city: 'Chicago' },
{ _id: ObjectId("..."), name: 'Alice', age: 28, city: 'New York' },
{ _id: ObjectId("..."), name: 'David', age: 25, city: 'New York' },
{ _id: ObjectId("..."), name: 'Bob', age: 35, city: 'San Francisco' },
{ _id: ObjectId("..."), name: 'Eve', age: 31, city: 'San Francisco' }
]
문서는 복합 인덱스 정의와 일치하게 먼저 city별로 알파벳순으로, 그리고 각 도시 내에서 age별로 가장 많은 나이부터 적은 나이 순으로 올바르게 정렬됩니다.