CodeGym /Kurslar /SQL SELF /Necə düzgün index növü seçmək olar

Necə düzgün index növü seçmək olar

SQL SELF
Səviyyə, Dərs
Mövcuddur

Artıq indexlərin nəzəriyyəsinə baş vurmuşuq, onların növləri ilə tanış olmuşuq, yaratmağı və silməyi öyrənmişik, həmçinin array və JSONB kimi mürəkkəb data tiplərini necə indeksləmək lazım olduğunu başa düşmüşük. İndi isə gəlin danışaq ki, məhz sənin tapşırıqların üçün ən effektiv işləyəcək indexi necə seçmək lazımdır — çünki səhv seçim böyük problemlərə səbəb ola bilər.

Təsəvvür elə ki, sənin database-in — kitabxanadır, sorğular isə kitab axtaran ziyarətçilərdir. Əgər kitablar sadəcə yerə səpələnibsə, axtarış sonsuz dolaşmaya çevrilir. Indexlər — bu, səliqəli rəflər və kataloqlardır, hansılar ki, lazım olanı tez tapmağa kömək edir, bütün kitabları bir-bir yoxlamadan.

Amma əgər uyğun olmayan rəf və ya kataloq qoysan, məsələn, range axtarışı üçün HASH-index istifadə etsən, bu elə bil kitabxanaçı kitabları ada görə axtarır, amma onun əlində yalnız buraxılış ilinə görə kataloq var — proses uzanacaq və hamı narazı qalacaq. Database-də bu, yavaş sorğular və sistemə əlavə yük kimi özünü göstərir.

Bu gün danışacağıq ki, indexi necə düzgün seçmək lazımdır ki, sorğuların uçsun, database isə yorulmasın. Əks halda nəticə bərbad olacaq: sorğular ləngiyir, resurslar yeyilir, kitabxanaçı (PostgreSQL) depressiyadadır.

Index seçimi üçün kriteriyalar: checklist

Index seçəndə özünə bir neçə sual ver:

  1. Bu sütunda hansı data tipi var?
    • Məsələn, rəqəmlər INTEGER, FLOAT tez-tez B-TREE index tələb edir, array-lər üçün — GIN, mətn sahələri isə artıq tapşırıqdan asılıdır.
  1. Ən çox hansı sorğuları edirsən?

    • WHERE field = value? Düz axtarış? Yəqin ki, sənə B-TREE və ya HASH uyğun olacaq.
    • Array və ya JSONB üzrə axtarış? GIN-ə bax.
    • Geo-məlumatlar, range-lər? GiST barədə düşün.
  2. Sənin datanda nə baş verir?

    • Əgər tez-tez insert və update olan cədvəlin varsa, artıq indexlərdən qaç, çünki bu, overhead-i artıracaq.
  3. Unikallıq təmin olunmalıdır?

    • Bu halda UNIQUE atributlu index istifadə etməlisən.

Case-lər: index seçiminin real nümunələri

Gəlin bir neçə real situasiyaya baxaq.

1. Sadə bərabərlik üzrə axtarış

Studentlər bazası ilə işləyirsən və email-ə görə student-i tez tapmaq istəyirsən:

SELECT * FROM students WHERE email = 'student@example.com';

Burada nə vacibdir? Bərabərlik üzrə axtarış edirik. Ən yaxşı seçim B-TREE indexdir, çünki dəqiq uyğunluq üçün əladır.

CREATE INDEX idx_students_email ON students (email);

Və ya, əgər email unikal olmalıdırsa:

CREATE UNIQUE INDEX idx_students_email_unique ON students (email);

2. Range üzrə axtarış

İndi təsəvvür elə ki, 18 yaşdan yuxarı olan studentləri tapmaq istəyirsən:

SELECT * FROM students WHERE age > 18;

Range axtarışı üçün də B-TREE əladır, çünki strukturu sırayla axtarış üçün nəzərdə tutulub.

CREATE INDEX idx_students_age ON students (age);

3. Array-lər üzrə filtrasiya

Səndə courses adlı cədvəl var, orada sütunlardan birində kursa yazılmış studentlərin ID-lərindən ibarət array saxlanılır. İstəyirsən ki, ID-si 123 olan studentin yazıldığı bütün kursları tapasan.

SELECT * FROM courses WHERE student_ids @> ARRAY[123];

Belə sorğular üçün GIN index idealdır, çünki array-lərlə işləmək üçün optimallaşdırılıb.

CREATE INDEX idx_courses_students_ids ON courses USING gin (student_ids);

4. JSONB-dən data çıxarmaq

Tutaq ki, səndə JSONB dataları olan cədvəl var, burada sifarişlər haqqında info saxlanılır. İstəyirsən ki, şəhəri "Moscow" olan bütün sifarişləri tapasan:

SELECT * FROM orders WHERE data->>'city' = 'Moscow';

Burada GIN index uyğundur, çünki JSONB-də açar və dəyərlərə görə effektiv axtarış verir.

CREATE INDEX idx_orders_data ON orders USING gin (data);

5. Coğrafi məlumatlar

Əgər geo-məlumatlarla işləyirsənsə, məsələn, müəyyən radiusa düşən bütün nöqtələri tapmaq istəyirsənsə, GiST index istifadə et. Bu index növü geometriya və range-lərlə əla işləyir.

CREATE INDEX idx_locations_geom ON locations USING gist (geom);

Fərqli indexlərin performans müqayisəsi

Gəlin real nümunəyə baxaq: studentləri email-ə görə axtarırıq. Cədvəldə 1 milyon qeyd var. Sorğunu fərqli indexlərlə və indexsiz yoxlayaq:

Ssenari İcra vaxtı
Indexsiz 1500 ms
B-TREE index ilə 2 ms
HASH index ilə 3 ms

Nəticə: bu halda B-TREE index sorğunu 500 dəfədən çox sürətləndirir.

Index seçərkən səhvlər

Ən yayılmış səhv — "birdən lazım olar" deyə hər sütuna index yaratmaqdır. Məsələn, hər sütunu indekslədin, amma sonra gördün ki, insert əməliyyatları bərk ləngiyib. Yadda saxla, index — hər yerdə və həmişə işləyən sehrli alət deyil. O, güclü alətdir, amma düzgün istifadə olunmasa, ziyan verə bilər.

Başqa tipik səhv — uyğun olmayan index növü seçməkdir. Məsələn, range axtarışı üçün HASH index istifadə edirsən və sorğular qəfil bərk ləngiyir. Çünki HASH index yalnız dəqiq axtarış üçün nəzərdə tutulub.

Index seçimi üçün tövsiyələr

  • Əgər tez-tez bərabərlik və ya sort üzrə axtarış edirsənsə, B-TREE istifadə et.
  • Dəqiq uyğunluq üçün, amma minimal yaddaş sərfiyyatı ilə, HASH istifadə etmək olar.
  • Əgər array və ya JSONB ilə işləyirsənsə, sənin seçimin — GIN.
  • Range və ya geo-məlumatlar üçün GiST istifadə et.

Və ən əsas məsləhət: sorğularını analiz etməyi unutma! EXPLAIN və EXPLAIN ANALYZE komandalarından istifadə et ki, PostgreSQL-in indexləri necə istifadə etdiyini və nəyi yaxşılaşdırmaq mümkün olduğunu görəsən.

EXPLAIN ANALYZE
SELECT * FROM students WHERE email = 'student@example.com';

Bu günlük bu qədər! İndi index seçmək üçün biliklərlə silahlanmısan, elə bil jeday öz işıq qılıncını seçir. Ehtiyatlı ol, lazım olmayan yerdə index yaratma və həmişə onların performansa necə təsir etdiyini yoxla.

2
Tapşırıq
SQL SELF, səviyyə, dərs
Bağlanıb
Qiymət aralığında axtarış üçün indeksdən istifadə
Qiymət aralığında axtarış üçün indeksdən istifadə
Şərhlər
TO VIEW ALL COMMENTS OR TO MAKE A COMMENT,
GO TO FULL VERSION