DISTINCT yerine IN veya EXISTS

SQL cümlelerinde JOIN kullanımı sonucu tekrarlayan kayıtlar ile karşılaştığımız oluyor. Bunları tekil hale getirmek için DISTINCT kelimesini kullanabiliriz(1), ancak distinct sıralama ve filtreleme işlemi yapacağından sorgunun performansını azaltacaktır.
DISTINCT kullanmak yerine mümkünse JOIN ifadesinde kullanılan tablo ve koşullar ayrılarak altsorguya dönüştürülebilir, aranan değere ulaşmak için performansı bu tür durumlarda JOIN den daha yüksek olan IN veya EXISTS kullanılabilir(2).

(1)
select distinct m.musteri_no
from tbl_musteri m
join tbl_hesap h
on h.musteri_no = m.musteri_no
and h.kayit_durum = 'A'
and m.musteri_no = 123456

(2)
select m.musteri_no
from tbl_musteri m
where exists (select h.musteri_no
from tbl_hesap h
where h.musteri_no = m.musteri_no
and h.kayit_durum = 'A')
and m.musteri_no = 123456

3 yorum:

T. E. Kalaycı dedi ki...

Merhaba,

Bir arkadaşımdan gelen bir soruyu sormak istiyorum. Yorum olarak atacaktı ama unuttu sanırım :)

"Daha önce hiç DISTINCT kullanmadım. LEFT.JOIN işimizi görmez mi? Yetmeyen nasıl bir örnek var?"

Mehmet KIŞ dedi ki...

Merhaba,
DISTINCT kelimesinin yaptığı işi, LEFT JOIN ile yapamıyoruz. DISTINCT ile yapmaya çalıştığımız, çalıştırdığımız sorguda dönen kayıtlardan tamamen aynı olan satırların sadece bir tanesinin alınmasını sağlamak.

LEFT JOIN i ise, eşleştireceğimiz tablolardan ikincisinde kayıt olmasa da, "birinci tablodaki kaydı, ikinci tablodan gelecek olanları NULL olarak gösterecek şekilde getir" diyebilmek için kullanıyoruz.

JOIN ya da INNER JOIN ifadeleri kullanıldığında dönecek olan veri seti, eşleştirilen iki tablodaki kayıtların kesişenleridir (A kesişim B), bu durumda sadece iki tabloda da olan kayıtlar dönecektir. LEFT JOIN kullandığımızda ise "tüm A tablosunu getir, yanında varsa B deki kayıtları da getir" demiş oluyoruz; A daki kaydın karşılığı B de yoksa, B ile ilgili alanlar NULL olarak dönecektir. Aynı şekilde RIGHT JOIN i kullanarak "tüm B tablosunu getir, yanında varsa A daki kayıtları da getir" demiş oluruz.

Adsız dedi ki...

Biraz "group by" ile, biraz da "join" ve "left join" ile oynadıktan sonra meseleyi anladım, iyi oldu. Teşekkürler.