Single Field Index(단일 필드 인덱스)?
사용방법?
Indexing 전략
- Sort 시 인덱스 순서를 고려해야 한다.
- 키로 잡은 field의 순서와 조회 시 순서가 동일해야 인덱스를 타고 조회한다. 그러므로 인덱스를 잡을 경우 키의 순서를 잡을때 신경써야 한다. 예를 들어 unitDatetime-globalSymbol 순서의 정렬은 지원하지만 globalSymbol-unitDatetime 정렬은 지원하지 않는다.
- 정렬 방향을 고려해야 한다.
- index를 사용한 정렬을 이용하기 위해서는 생성된 인덱스의 정렬 방향과 같거나 역으로 조회하는 쿼리만 인덱스를 탄다.
- index 타는 쿼리 : sort({ "unitDatetime": -1, "globalSymbol": 1 }) 혹은 sort({ "unitDatetime": 1, "globalSymbol": -1 })
- index 타지 않는 쿼리 : sort({ "unitDatetime": 1, "globalSymbol": 1 }) 혹은 sort({ "unitDatetime": -1, "globalSymbol": -1 })
- Prefixes
- 복합 인덱스의 가장왼쪽 필드를 시작으로 만들어진 인덱스의 부분집한 인덱스를 말한다.
- 예를 들어보면, { unitDatetime:1, buyVolUsd:1, sellVolUsd:1 }로 이루어진 Compound Index는 { unitDatetime:1 }, { unitDatetime:1, buyVolUsd:1} 앞의 2개의 Index Prefixes를 가지고 있다.
- 이 Index Prefixes는 인덱스처럼 동작을 한다. sort({ unitDatetime: 1 }), sort.({ unitDatetime: 1, buyVolUsd:1 })로 정렬 조회를 하면 위의 인덱스 Prefixes를 통해 조회가 된다.
- non-prefix 조회
- 정렬 조회 시에 prefix가 아닌 경우도 조회가 가능하다. 단, Equality 상태인 경우에만 가능하다.
- db.collection.find({ unitDatetime: ISODate("2022-06-25T14:45:00.000+0000") }).sort({ buyVolUsd:1, sellVolUsd:1 }) 선행인 unitDatetime이 정렬조건에 없지만 Equality 상태이므로 인덱스를 사용한 조회가 가능하다.
추가로 기존 데이터가 중복일 경우 중복을 제거하는 방법이다.
아래 코드를 몽고 쉘에서 작성하여 실행함으로써 중복 데이터 제거 가능하다.
var duplicates = [];
db.getCollection("traderposition.total")
.aggregate(
[
{ $group: {
// _id는 group으로 묶을 field 세팅
_id: { unitDatetime:"$unitDatetime", symbol:"$symbol" },
// 아래의 field는 grouping의 결과로 보여줄 field
dups: { "$addToSet": "$_id" },
count: { "$sum": 1 }
}
},
{ $match: {
count: { "$gt": 1 }
}
}
]
) // You can display result until this and check duplicates
.forEach(function(doc) {
doc.dups.shift(); // First element skipped for deleting
doc.dups.forEach(function(dupId) {
duplicates.push(dupId); // Getting all duplicate ids
})
}
)
// 삭제 대상 출력
printjson(duplicates);
// 대상을 가지고 실제 삭제
db.getCollection("traderposition.total").remove({_id:{$in:duplicates}}) // $in -> rdbms의 in 과 비슷한 역할