Может ли составной индекс обслуживать несколько запросов

У меня есть коллекция по названиям фабрик.

В этой коллекции будут два типа запросов, которые будут попадаться в коллекцию с именем фабрики, показанные ниже

db.factories.find({ city: "New York", state: "NY"} );


db.factories.find({ city: "New York", state: "NY" , country:"US"} );

Мой вопрос: если я создаю составной индекс, как показано ниже, будет ли он обслуживать оба запроса?

db.factories.ensureIndex({city:1,state:1,country:1},{"unique" : false})

Ответ 1

Да.

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

Поля в составном индексе идут от первого до последнего значениями всех детей, вложенных в родителей. Это означает, что если у вас было три документа типа:

[{
    _id:{},
    a: 1,
    b: 2,
    c: 3
},{
    _id:{},
    a: 4,
    b: 5,
    c: 6
},{
    _id:{},
    a: 7,
    b: 8,
    c: 9
}]

И сделал индекс на:

db.collection.ensureIndex({a:1,b:1,c:1})

Индекс будет выглядеть примерно так: {1: [2,3]}, причем первое значение является самым левым полем, а два других - значениями, которые находятся под этим самым большим значением.

Конечно, это не так, как выглядит индекс, я просто сделал это, чтобы сделать его человеком доступным для всех. Чтобы узнать, как именно на самом деле сформирован индекс, вы можете посмотреть несколько презентаций, которые я считаю хорошими как дефакто, чтобы всегда смотреть это: http://www.mongodb.com/presentations/storage-engine-internals на внутренних устройствах хранения.

Итак, это означает, что MongoDB работает, чтобы выбрать этот индекс с помощью префиксного метода, в котором он скажет, что a и a,b являются префиксами индекса и могут использовать эти поля для извлечения всех других значений, необходимых из индекса.

Префикс таким образом означает, что индекс не будет работать, если вы запросили:

db.collection.find({state:"NY",country:"YS"});
db.collection.find({state:"NY"});
db.collection.find({country:"YS"});

Хорошо отметить, что порядок в запросе НЕ СОБИРАЕТСЯ. Вы можете сделать поля в запросе в любом порядке, где это имеет значение, в ИНДЕКСЕ.

В любом случае, это простой пример того, почему запросы будут использовать этот единственный индекс.