Özet: Fonksiyonel tarzda yazılan sorgularda, normal index’in işe yaramadığını, “fonksiyonel index” oluşturmanın etkisini ve gerekliliğini anlatıyor.

 

SQL Sorgularında datayı çekerken ilgili kolonlara full scan veya üzerinde index varsa index scan yaparak gider. Index kullanımı çoğu zaman dataya daha çabuk erişmemizi sağlar.

Bazen karşılaştığımız ;

  • Bu sorgu çok yavaş geliyor. Üzerinde index olmasına rağmen index’i kullanmıyor. Neden acaba?

gibi sorularla gelinebiliyor.

Bunun muhtemel nedenlerinde bir tanesi where koşulu içindeki bir durum olduğunu görebiliyoruz. Koşulda functional (fonksiyonel) bir ifade var.

Bunun için Oracle bize Function-Based Index opsiyonunu sunuyor. Function-Based Index’in sorgu iyileştirmesine etkisini aşağıdaki örnekler üzerinden görelim.

Bir tablo oluşturalım ve bu tabloya random 500.000 kayıt atalım

CREATE TABLE func
(
 id NUMBER (10) NOT NULL,
 rand_st VARCHAR2 (40) NOT NULL,
 rand_st2 VARCHAR2 (40) NOT NULL,
 rand_st3 VARCHAR2 (1) NOT NULL,
 rand_date DATE
);
BEGIN
 FOR func_loop IN 1 .. 500000
 LOOP
 INSERT INTO func
 VALUES (func_loop,
 DBMS_RANDOM.STRING ('A', 7),
 DBMS_RANDOM.STRING ('A', 7),
 DBMS_RANDOM.STRING ('A', 1),
 TRUNC (SYSDATE + DBMS_RANDOM.VALUE (0, 75)));

COMMIT;
 END LOOP;
END;
/
  • İlk başta index olmadan aşağıdaki sorgunun execution planına bakalım

func_indx 1

Üzerinde index olmadığı için tabloya full gitti, ciddi performans kaybı oldu..!

 

  • Şimdi “rand_st” kolonu üzerine normal bilinen yöntemle bir index oluşturalım.
CREATE INDEX fucn_idx ON func (rand_st);

func_3

Where koşulu functional(fonksiyonel) olduğundan bizim oluşturduğumuz index’i kullanmamış ve tabloya yine full gitti..!

 

  • “rand_st” kolonu için Function-Based Index oluşturalım şimdi..!
create index fucn_idx2 ON func (UPPER(rand_st));

func_indx 2

Şimdi gördüğümüz gibi oluşturduğumuz index’i kullanmış ve sorgunun cost ve bytes’i düştü, performansta gözle görülür bir artış oldu..!

 

  • Bu yöntem, birleştirilmiş index’ler içinde çalışır. Şimdi rand_st ve rand_date için index oluşturalım.
CREATE INDEX fucn_idx3 ON func (UPPER(rand_st), rand_date);

func_indx 5.jpg

Gördüğümüz gibi yine index’i kullandığını görüyoruz.