Bei einer einfachen Standardabfrage (ohne limit()
oder sort()
oder irgendetwas Besonderes angewendet), das eine Filterbedingung für zwei Felder hat (wie in name
und age
in Ihrem Beispiel), um die resultierenden Dokumente zu finden, wird MongoDB entweder:
- Führen Sie einen vollständigen Sammlungsscan durch (Lesen Sie jedes Dokument in der gesamten Sammlung, parsen Sie den BSON, finden Sie die fraglichen Werte, testen Sie sie mit der Eingabe und geben Sie jedes Dokument zurück/verwerfen Sie es):Dies ist sehr I/O-intensiv und daher langsam.
- benutze einen Index das eines der Felder enthält (verwenden Sie den Indexbaum, um eine relevante Teilmenge von Dokumenten zu finden, gefolgt von einem Scan davon):Abhängig von Ihrer Datenverteilung/Indexselektivität kann dies sehr schnell sein oder kaum einen Nutzen bringen (stellen Sie sich einen Index auf
age
in einem Datensatz von Millionen von Menschen zwischen 30 und 40 Jahren --> jede Suche würde immer noch eine endlose Anzahl von Dokumenten ergeben). - benutze zwei Indizes die zusammen beide fraglichen Felder enthalten (beide Indizes laden, Schlüsselsuchen durchführen, dann die Schnittmenge der Ergebnisse berechnen):Auch dies kann je nach Ihrer Datenverteilung zu einer besseren Leistung führen oder nicht. Es sollte jedoch in den meisten Fällen schneller sein als #2. Ich wäre jedoch überrascht, wenn es wirklich 10x langsamer wäre als #4 (wie Sie erwähnt haben).
- Verwenden Sie einen zusammengesetzten Index (zwei aufeinanderfolgende Schlüsselsuchen führen sofort zu den erforderlichen Dokumenten):Dies ist die schnellste Option von allen, da es die wenigsten und billigsten Operationen erfordert, um zu den richtigen Dokumenten zu gelangen. Um die größtmögliche Wiederverwendung zu gewährleisten (nicht die Leistung, die davon nicht beeinträchtigt wird), sollten Sie im Allgemeinen zuerst mit dem selektivsten Feld beginnen, also in Ihrem Fall wahrscheinlich
name
und nichtage
da viele Leute das gleicheage
haben (so geringe Selektivität) im Vergleich zuname
(höhere Selektivität). Diese Wahl hängt jedoch auch von Ihrem konkreten Szenario und den Abfragen ab, die Sie für Ihre Datenbank ausführen möchten. Es gibt einen ziemlich guten Artikel im Internet darüber, wie man am besten einen zusammengesetzten Index definiert, der verschiedene Aspekte Ihrer spezifischen Situation berücksichtigt:https://emptysqua.re/blog/optimizing-mongodb-compound-indexes
Weitere zu berücksichtigende Aspekte sind:Indexaktualisierungen haben ihren Preis. Wenn Ihnen jedoch nur die reine Lesegeschwindigkeit wichtig ist und Sie nur ab und zu ein paar Updates haben, sollten Sie sich für mehr/größere Indizes entscheiden.
Und last but not least (!) der viel zu oft gebrauchte Ratschlag:Profilieren Sie Ihr System mit echten Daten und vielleicht sogar realistischen Lastszenarien. Und messen Sie auch weiter, wenn sich Ihre Daten/Ihr System im Laufe der Zeit ändern.
Zusätzliche Informationen:https://docs.mongodb.com/manual/core/query-optimization/index.html
https://dba.stackexchange.com/questions/158240/mongodb-index-intersection-does-not-eliminate-the-need-for-creating-compound-in
Indexschnittpunkt vs. zusammengesetzter Index?
Mongodb zusammengesetzter Index vs. Index-Schnittpunkt
Wie wirkt sich die Reihenfolge der zusammengesetzten Indizes in MongoDB auf die Leistung aus?
In MongoDB verwende ich eine große Abfrage, wie ich einen zusammengesetzten Index oder einen einzelnen Index erstelle, damit sich meine Antwortzeit erhöht