Clustered Index vs Non-Clustered Index

 Tablo üzerinde bir veri araması yaptığımızı varsayalım. Veritabanında saklanan verilerin sayısı arttıkça bu performansta düşüklüğe neden olur. Dağınık yapıda olan verilerde istenilen veriyi aramak için tablo taraması işlemi yapılır. Sql’de indexe sahip olmayan tablolara heap adı verilir. Heap bir tabloda bir select çektiğimizde, sql tablodaki kaydı bulabilmek için bütün kayıtları bir bir dolaşır. Hatta kaydı bulsa dahi, birden fazla kayıt olma ihtimaline karşı tabloyu dolaşmaya devam eder. Bu da sql için ciddi bir performans kaybına yol açar. Bu işlemi küçük boyutlu bir tabloda yapmak kolaydır. Ancak artan veri miktarına göre bu işlem vakit kaybettirir. Indexler ise tablolardan veri çekmek için gerekli sorgular çalıştırılırken gereken süreyi azaltmak için kullanılırlar. İşte tam da bu noktada , sorgu işlemlerimi yaparken clustered index ve non-clustered index kavramlarını bilmemiz sql performansı açısından işimize yarayacaktır.

Yukarıda bahsi geçen olayı somut bir şekilde örnekleyelim.

Create table [tblEmployee]
(
  [Name] nvarchar(50),
  [Salary] int,
  [Gender] nvarchar(10),
  [City] nvarchar(50)
)


Tablomuzda aşağıdaki gibi binlerce hatta yüzbinlerce kayıt olduğunu varsayalım. Bu tabloda kayıtları spesifikleştiren hiç bir index bulunmamaktadır. Bu yüzden insert durumunda kayıtlar tamamen free olarak tabloya yerleşir.   Bu gibi tablodan select * from tblEmployee where Name = ‘Tobb’ şeklinde bir select attığımzda , sql kolonları unique yapacak bir veriye sahip olmadığı için 1. kayıttan itibaren sırayla Name’i Tobb olan kaydı aramaya başlar. Bu tip arama işlemine scan denir. Bulsa dahi birden fazla Tobb isimli kayıt olup olmadığını bilmediğinden, aramaya devam eder. Al sana performans problemi 🙂

insert into tblEmployee values('Sam',2500,'Male','London')
insert into tblEmployee values('john',2500,'Male','London')
insert into tblEmployee values('Tobb',2500,'Male','London')
insert into tblEmployee values('Crixus',2500,'Male','London')
...

Problemi anladıysak artık bu gibi performans kayıplarına düşmemek için Clustred index ve non-clustred index kavramlarına geçiş yapabiliriz.

Clustred Index

Clustred index , veriyi sql’de fiziksel olarak sıraya sokan yapıdır. Aslında hepimiz clustred index’i tablolarımızda kullanıyoruz. Tablolarımıza tanımladığımız her bir Primary key aslında bir Clustred index yapısıdır. Çünkü tablolarımız bu pk’ya göre fiziksel olarak sıralanır.

Yukarıdaki tablo yapısını tekrardan primary key ile oluşturalım.

Create table [tblEmployee]
(
   [Id]  int Primary Key,
   [Name] nvarchar(50),
   [Salary] int,
   [Gender] nvarchar(10), 
   [City] nvarchar(50)
)

artık tablomuz bir clusted indexe sahip. Bunu somut olarak görebilmek için aşağıdaki sorguyu çalıştıralım.

Execute sp_helpindex tblEmployee

Şimdi tablomuza insertlerimizi yeniden atalım.

insert into tblEmployee values(3, 'Sam' ,2500,'Male' ,'London')
insert into tblEmployee values(1, 'john' ,2500, 'Male' ,'London')
insert into tblEmployee values(2, 'Tobb' ,2500, 'Male' ,'London')
insert into tblEmployee values(4, 'Crixus' ,2500, 'Male' ,'London')
...

bu insertlerin atılış sırası ne olursa olsun sql bunları otomatik olarak clustered index olan Id’ye göre dizecektir. Ve hedefe yönelik bir search ile index üzerinden hızlı bir şekilde bulabilenecek hale gelecektir.

clustered index ile ilgili önemli noktalar

  • Her tabloda yalnızca 1 adet clustered index olabilir.
  • Tablodaki bir clustered index pk olabileceği gibi aynı zamanda birden fazla kolonun birleşiminden oluşan bir yapı da olabilir. Buna composite clustered index denir.
  • Sql query sonucu sıralı dataları dönerken aynı sırada döner .Aşağıdaki query ile 2 kolona bağlı clustered index yaratmış olduk. Bu querynin bize söylediği şey , tablomdaki kayıtları Gender’a göre diz , genderi aynı olanları da artan sırada salary’e göre diz. Siz insertlerinizi ne şekilde atarsanız atın, dizilim bu yönde olacaktır.
    create clustered index myClusteredIndex On tblEmployee (Gender Desc,Salary Asc)
    
    Drop index tblEmployee
    
    

Non-Clustered Index 

Non-clustered indexlemede durum biraz daha farklıdır. Bir kolonu Non-clustered index olarak indexlediğinizde, arka tarafta yeni bir tablo oluşur ve bu tablo sizin indexlediğiniz kolona karşılık kolon adresini tutar. Yani bir nevi pointer yapısı gibi düşünebilirsiniz. Nonclustered indekste verilere direkt erişilemez. Elde edilen indeksleme yapısına erişmek için kümelenmiş indeks yapısı kullanılmış olur. Verileri herhangi bir alana göre sıralandığında erişim kümelenmiş indeks üzerinden anahtar değer referans alınarak yapılır. 

Non-cluster indexlemeyi kafanızda oturtabilmek için kitap örneğini düşünebilirsiniz. Kitapların başında içerik kısmı vardır. Bu içerik kısmında her bir konu başlığının hangi sayfa numarasında veya sayfa numaraları aralığında olduğunu gösterir. Siz kitabı açtığınızda önce içerik sayfasına bakarsınız. Daha sonra aradığınız içeriğin sayfasını ya da sayfa aralığını öğrenip direkt olarak bu sayfalara geçersiniz. Non-cluster index de tam olarak bunu yapmakta.

Non cluster index oluşturmak için aşağıdaki sorguyu kullanabiliriz.

create nonclustered index myClusteredIndex On tblEmployee (Gender Desc,Salary Asc)

non clustered index ile ilgili önemli noktalar

  •  Bir tablonun birden fazla non-cluster indexi olabilir.
  •  Bir tabloya non-cluster index eklemek, tablonun fiziksel dizilimini etkilemez.

You may also like...

1 Response

  1. 28 Ekim 2019

    […] Clustered Index ve Non-Clustered Index Kavramı […]

Bir cevap yazın

E-posta hesabınız yayımlanmayacak. Gerekli alanlar * ile işaretlenmişlerdir