sql >> Database teknologi >  >> NoSQL >> MongoDB

hvordan man strukturerer et sammensat indeks i mongodb

Det er mange spørgsmål i et indlæg;) Lad mig gennemgå dem i en praktisk rækkefølge :

  • Hver forespørgsel kan højst bruge ét indeks (med undtagelse af $eller klausuler på øverste niveau og sådan). Dette inkluderer enhver sortering.
  • På grund af ovenstående vil du helt sikkert have brug for et sammensat indeks for dit problem frem for separate indekser pr. felt.
  • Felter med lav kardinalitet (altså felter med meget få unikke værdier på tværs af dit datasæt) bør normalt ikke være i indekset, da deres selektivitet er meget begrænset.
  • Rækkefølgen af ​​felterne i dit sammensatte indeks har betydning, og det samme gør den relative retning af hvert felt i dit sammensatte indeks (f.eks. "{navn:1, alder:-1}"). Der er meget dokumentation om sammensatte indekser og indeksfeltvejledninger på mongodb.org, så jeg vil ikke gentage det hele her.
  • Sortering vil kun bruge indekset, hvis sorteringsfeltet er i indekset og er feltet i indekset direkte efter det sidste felt, der blev brugt til at vælge resultatsættet. I de fleste tilfælde vil dette være det sidste felt i indekset.

Så du bør slet ikke inkludere status i dit indeks, da når først indeksvandringen har elimineret langt de fleste dokumenter baseret på felter med højere kardinalitet, vil den højst have 2-3 dokumenter tilbage i de fleste tilfælde, hvilket næppe er optimeret af et statusindeks (især da du nævnte, at de 2-3 dokumenter med stor sandsynlighed alligevel har samme status).

Den sidste bemærkning, der er relevant i dit tilfælde, er, at når du bruger intervalforespørgsler (og det gør du), vil den alligevel ikke bruge indekset til sortering. Du kan tjekke dette ved at se på "scanAndOrder"-værdien af ​​din explain(), når du har testet din forespørgsel. Hvis denne værdi eksisterer og er sand, betyder det, at den vil sortere resultatsættet i hukommelsen (scan og orden) i stedet for at bruge indekset direkte. Dette kan ikke undgås i dit specifikke tilfælde.

Så dit indeks bør derfor være :

db.posts.ensureIndex({start:1, end:1})

og din forespørgsel (rækkefølgen er kun ændret for klarhedens skyld, forespørgselsoptimering vil køre din oprindelige forespørgsel gennem den samme udførelsessti, men jeg foretrækker at sætte indekserede felter først og i rækkefølge) :

db.posts.find({start: {$lt: today}, end: {$gt: today}, status: {$gte:0}}).sort({sortOrder:1})



  1. Opretter forbindelse til Redis, der kører i Docker Container fra værtsmaskine

  2. Laravel - Løbende job i rækkefølge

  3. MongoDB $first Aggregation Pipeline Operator

  4. Hvordan ignorerer man nuller, mens man fjerner et MongoDB-dokument?