2011-02-06 2 views
0

(방문자)의 하위 객체에 사이트 사용 이벤트가 기록됩니다.MongoDB에서 Sub 객체를 쿼리하면 색인이 사용되지 않습니다.

{ "_id" : ObjectId("4d4c695794b332a0740009bd"), "evs" : [ 
    { 
      "ev" : "Visit Home Page", 
      "d" : 1, 
      "s" : 1 
    }, 
    { 
      "ev" : "Buy Product", 
      "d" : "110.10", 
      "upc" : 1234, 
      "s" : 1 
    }, 
    { 
      "ev" : "Sign up to newsletter", 
      "d" : "1", 
      "s" : 1 
    } 
]} 

내가 'evs.s'에 인덱스를 가지고,하지만 난 evs.s에 검색 할 때 인덱스를 사용하지 : 여기에 데이터 구조의 기본 예입니다

db.visitors.find({'evs.s':0}).explain() 
{ 
    "cursor" : "BtreeCursor evs.s_1", 
    "nscanned" : 33361, 
    "nscannedObjects" : 33361, 
    "n" : 33361, 
    "millis" : 311, 
    "nYields" : 105, 
    "nChunkSkips" : 0, 
    "isMultiKey" : false, 
    "indexOnly" : false, 
    "indexBounds" : { 
      "evs.s" : [ 
        [ 
          0, 
          0 
        ] 
      ] 
    } 
} 

이 쿼리는 311 밀리 초가 걸리고 모든 개체를 검색합니다. 여기

인덱스이다 db.visitors.getIndexes()

{ 
    "ns" : "tracking.visitors", 
    "unique" : false, 
    "key" : { 
    "evs.s" : 1 
    }, 
    "name" : "evs.s_1", 
    "v" : 0 
} 

답변

2

사용자의 쿼리는 실제로 Explain 출력 ("BtreeCursor evs.s_1")의 커서 유형에 표시된대로 색인을 사용합니다. 인덱스를 사용하지 않았다면 "BasicCursor"가됩니다.

입력 데이터에서 evs.s가 색인을 생성하는 데 매우 효율적인 키가 아닌 것처럼 보입니다. evs.s의 값이 모두 1 또는 0이면 색인은 항상 많은 수의 일치 항목을 누르게됩니다.

내 생각에 귀하의 쿼리는 전체 테이블 스캔을 수행하지 않았지만 실제로 인덱스에 값이 evs.s = 0 인 레코드가 많이 있습니다. . 당신은

db.visits.find의 출력 비교할 수

({evs.s : 0}) 계산();

db.visits.find ({evs.s : 1}). count();

db.visits.find(). count();

이것을 확인하십시오.

1) 당신은 더 뚜렷한 값이 다른 인덱스를 사용할 수 있습니다

는이 속도를 위해 할 수있는 몇 가지가 있습니다. 이렇게하면 각 쿼리의 검색 공간이 줄어 듭니다.

2) 쿼리에 제한 문을 추가 할 수 있습니다. 제한된 문서가 발견되면 색인 검색이 중지됩니다.

+0

네, 그렇습니다. 10,000을 효율적으로 색인 생성하는 실제적인 방법은 없습니다. Limit를 사용하면 쿼리 속도가 빨라집니다. – Lerchmo

0

"커서": "BtreeCursor evs.s_1는"

인덱스 가 사용된다는 것을 의미한다.

관련 문제