sql >> Database teknologi >  >> RDS >> PostgreSQL

unaccent() forhindrer indeksbrug i Postgres

IMMUTABEL variant af unaccent()

For at afklare misinformationen i det aktuelt accepterede, forkerte svar :
Udtryksindekser tillader kun IMMUTABLE funktioner (af indlysende årsager) og unaccent() er kun STABLE . løsningen, du foreslog i kommentaren er også problematisk. Detaljeret forklaring og en rigtig løsning for det :

Afhængigt af indholdet af tags->name det kan være nyttigt at tilføje unaccent() til udtryksindekset, men det er ortogonalt i forhold til spørgsmålet, hvorfor indekset ikke blev brugt:

Faktisk problem/løsning

Operatøren LIKE i din forespørgsel er subtilt forkert (højst sandsynlig). Det gør du ikke ønsker at fortolke 'Weststrasse' som søgemønster, vil du matche den (normaliserede) streng, som den er. Erstat med = operator, og du vil se en (bitmap) indeksscanning med dit nuværende indeks, uanset af funktionen volatilitet af unaccent() :

SELECT * FROM germany.ways
WHERE lower(tags->'name') = lower(unaccent('unaccent','Weststrasse'))

Hvorfor?

Den højre operand af LIKE er et mønster . Postgres kan ikke bruge et almindeligt btree-indeks til mønstermatchning ( undtagelser gælder ). En LIKE med en almindelig streng som mønster (ingen specialtegn) kan optimeres med et lighedstjek på btree-indekset. Men hvis der er specialtegn i strengen, dette indekset er ude.

Hvis der er en IMMUTABLE funktion til højre for LIKE , kan den evalueres med det samme, og den nævnte optimering er stadig mulig. I henhold til dokumentation om Funktionsvolatilitetskategorier :

Det samme er ikke muligt med en mindre funktionsvolatilitet (STABLE eller VOLATILE ). Det er derfor din "løsning" med at forfalske en IMMUTABLE unaccent() så ud til at virke, men det er virkelig at sætte læbestift på en gris.

For at gentage:

  • Hvis du vil arbejde med LIKE og mønstre, brug et trigramindeks .
  • Hvis du ikke vil arbejde med LIKE og mønstre, brug lighedsoperatoren =



  1. SQL Express til produktion?

  2. Hvordan kan jeg løse ORA-00911:ugyldig tegnfejl?

  3. Java EE/JPA måde at tilføje nye tabeller/enheder til databasen

  4. Udlejning af biler er lige så enkelt som at køre:En datamodel for et biludlejningsfirma