sql >> Database teknologi >  >> RDS >> Sqlserver

optimer nærmeste naboforespørgsel på 70 millioner rumlig punktsky med ekstrem høj tæthed på SQL Server 2008

Beklager, men dette er ikke et SQL-svar, men en måde at få forudsigelig ydeevne på under forudsætning af visse begrænsninger på dine data.

Hvor ofte ændres dataene? Hvis det er muligt, kunne du forudberegne en graf over hver enheds 5 nærmeste naboer og bruge den til at fremskynde dit valg.?

Hvis disse data for det meste er skrivebeskyttede, så...

Hvor ligeligt er disse point fordelt? Hvis fordelingen er forholdsvis jævn og velkendt, kan du så rulle din egen rumlige kortlægning ved at samle hver koordinat og indeks i en hash-tabel.

Hvis du ikke har brug for at have dataene i databasen, skal du flytte dem ud til en hukommelseskortfil for hurtige hash-opslag. (70m rekorder burde nemt passe i hukommelsen).

Jeg har brugt denne arkitektur til at generere sub-millisekunder opslag for displayannoncering og søgemaskinerelevans.

==Uddybning==

Du laver ganske enkelt et gitter af firkanter med fast størrelse (som et skakbræt), og du kortlægger hvert punkt i gitteret, og du opretter en liste over de objekter, der hører til i hver af gitterboksene -- hvis du justerer størrelsen af ​​hver boks korrekt, bør du i gennemsnit have 5-50 point i hver firkant -- Dette er i princippet et quad-træ, men uden træet for nemheds skyld.

For hver bucket, der er tom, efter at du har spredt alle data i buckets, tilføjer du oplysninger om, hvilke nærmeste buckets der indeholder data.

Du kan nu nummerere hver bucket fra venstre-til-højre-line-ny-line, så hver bucket har et unikt nummer, som kan beregnes ud fra koordinaterne -- og du indsætter hver bucket i en hash-tabel, eller hvis pladsen tillader det lige som en lige opslagstabel.

Når du nu har din forespørgsel, beregner du blot, hvilken bucket, der vil mappe til, og du vil enten få en liste over objekter i den bucket, eller du vil få en 'tom' bucket, som indeholder pointerne til den nærmeste bucket, der har indhold .

Det vil give dig den første kandidatliste over objekter, som du leder efter, og nu skal du simpelthen bare løbe og se, hvilken der er tættest på.

I 99 % af tilfældene ville det være det -- men hvis du er bekymret for, at der (a) enten er nogle kandidater i de næste-over-spande, som faktisk er tættere på, så tjek bare de 8 omgivende spande, og se om du kan finde nogen nærmere der.

Hvis du nu også vil have en liste over alle de objekter, der er tættest på, så beregn også et simpelt netværk af 5 nærmeste naboer for hver objct, så du ender med en datastruktur som A->{B,C,D ,E,F}, B->{A,D,G,H,I}, C->{A,J,K,G,M}...

Det vil danne et simpelt netværk, som du nu kan krydse med en variation af Dijkstra her for at få hele punktet, der støder op til dit nærmeste punkt.

Opbygningen af ​​datastrukturerne vil tage tid, men når først det er gjort, og det er gjort rigtigt, kan opslag og returnering af et datasæt ske på sub millisekunder (ikke inklusive nogen http eller off-box kommunikation af årsag)

Håber dette hjælper.



  1. PHP PDO undslipper spørgsmålstegn, så den tror ikke, det er en pladsholder

  2. At få to tæller og derefter dele dem

  3. PostgreSQL - Tilføj nøgle til hvert objekt i et JSONB-array

  4. GRUPPER EFTER og BESTIL EFTER