2013-09-04 4 views
0

Я отложил кластер mongoDB хешированным _id. Я проверил размер индекса, там лежит _id_hashed индекс, который занимает много места:Что такое индекс _id_hashed для mongoDB?

"indexSizes" : { 
      "_id_" : 14060169088, 
      "_id_hashed" : 9549780576 
    }, 

MongoDB руководство говорит, что индекс на sharded ключа создается, если вы шард коллекции. Наверное, это причина, по которой индекс _id_hashed.

Мой вопрос: что такое _id_hashed index, если я только запрашиваю документ по полю _id? могу ли я удалить его? так как занимает слишком много места.

ps: кажется, что mongoDB использует индекс _id при запросе, а не индекс _id_hashed. план выполнения для запроса:

"clusteredType" : "ParallelSort", 
    "shards" : { 
      "rs1/192.168.62.168:27017,192.168.62.181:27017" : [ 
        { 
          "cursor" : "BtreeCursor _id_", 
          "isMultiKey" : false, 
          "n" : 0, 
          "nscannedObjects" : 0, 
          "nscanned" : 1, 
          "nscannedObjectsAllPlans" : 0, 
          "nscannedAllPlans" : 1, 
          "scanAndOrder" : false, 
          "indexOnly" : false, 
          "nYields" : 0, 
          "nChunkSkips" : 0, 
          "millis" : 0, 
          "indexBounds" : { 
            "start" : { 
              "_id" : "spiderman_task_captainStatus_30491467_2387600" 
            }, 
            "end" : { 
              "_id" : "spiderman_task_captainStatus_30491467_2387600" 
            } 
          }, 
          "server" : "localhost:27017" 
        } 
      ] 
    }, 
    "cursor" : "BtreeCursor _id_", 
    "n" : 0, 
    "nChunkSkips" : 0, 
    "nYields" : 0, 
    "nscanned" : 1, 
    "nscannedAllPlans" : 1, 
    "nscannedObjects" : 0, 
    "nscannedObjectsAllPlans" : 0, 
    "millisShardTotal" : 0, 
    "millisShardAvg" : 0, 
    "numQueries" : 1, 
    "numShards" : 1, 
    "indexBounds" : { 
      "start" : { 
        "_id" : "spiderman_task_captainStatus_30491467_2387600" 
      }, 
      "end" : { 
        "_id" : "spiderman_task_captainStatus_30491467_2387600" 
      } 
    }, 
    "millis" : 574 

ответ

2

MongoDB использует подход, основанный на диапазонах. Если вы решили использовать хеширование на основе хеширования, у вас должен быть хешированный индекс на клавише осколка и он не может отбросить его, поскольку он будет использоваться для определения осколка, используемого для любых последующих запросов (обратите внимание, что есть открытый билет, позволяющий вам отказаться индексу _id после хэширования индексов разрешено быть уникальным SERVER-8031).

Относительно того, почему запрос, по-видимому, использует индекс _id, а не индекс _id_hashed - я провел несколько тестов, и я думаю, что оптимизатор выбирает индекс _id, потому что он уникален и дает более эффективный план. Вы можете увидеть подобное поведение, если вы очертите другой ключ, который имеет ранее существовавший уникальный индекс.

+0

, который отвечает на мой вопрос. спасибо, Джефф. – zach

0

Если вы sharded на хэшированном _id то, что это тип индекса, который был создан.

Когда вы сделали sh.shardCollection('db.collection', { _id:"hashed" }) вы сказали, это вы хотите использовать хэш _id в качестве ключа шарда который требует индекса хэширования _id.

Итак, нет, вы не можете отказаться от него.

+0

Да, я нашел это в руководстве mongoDB. что меня озадачивает: для чего этот хешированный индекс? можете ли вы подробнее рассказать о том, как mongoDB будет использовать этот индекс? Благодарю. – zach

+1

, если вы хотите использовать хэш значений _id для вашего ключа осколка, mongoDB потребуется индекс на клавише осколка (для быстрого поиска диапазонов), и поэтому ему нужен индекс хэшей _id. (в дополнение к индексу фактических значений _id, которые являются обязательными). –

+0

Почему mongoDB нужно искать диапазоны в хэшированном ключевом индексе? при переносе кусков в другие осколки? – zach

0

В документации подробно описано, что такое хешированный индекс, который вызывает у меня проблемы с тем, как вы прочитали документацию, но не знаете, для чего нужен хешированный индекс.

Указатель предназначен, главным образом, для остановки горячих точек в ключах осколков, которые могут быть распределены неравномерно с их чтением/записью.

Итак, представьте себе поле _id, это постоянно увеличивающийся диапазон, все новые _id s будут после, это означает, что вы всегда пишете в конце своего кластера, создавая горячую точку.

Что касается чтения, то это может быть довольно распространено, поскольку вы читаете только самые новые документы, так как это означает, что верхний диапазон ключа _id является единственным, который используется для создания горячей точки как для чтения, так и для записи в верхнем диапазон кластера, в то время как остальная часть вашего кластера просто сидит там без дела.

Хеш-индекс принимает этот плохой ключ осколка и хэширует его таким образом, что он никогда не увеличивается, но вместо этого создаст равномерно распределенный набор данных для чтения и записи, надеясь объединить весь набор, который будет использоваться для операции.

Я бы настоятельно рекомендовал вам не удалять его.

+0

для горячей точки, поэтому я использовал хэшированное поле _id в качестве ключа. – zach

+0

@zach так держитесь, что вы думаете? – Sammaye

+0

Возможно, вы неправильно поняли мой вопрос. Я понимаю, что такое горячая точка, поэтому я использовал хешированное _id-поле как ключ осколка, а не только поле _id. по-другому, если я просто использую поле _id в качестве ключа осколка, ситуация проста: у меня будет только индекс _id_. mongoDB использует этот индекс для поиска запроса в поле _id. когда я использовал хешированный _id в качестве ключа осколка, MongoDB генерирует еще один _id_hashed индекс, я не понимаю, когда & как mongoDB использует этот индекс? – zach