SQL Server'da Query Hint Kullanımı

SQL Server'da Query Hint Kullanımı

Veritabanı sistemlerinde "hint", yani "ipucu" kullanılmarı aslında düşündüğümüzden çok daha faydalı bir şey. Bu yazımızda, yazdığınız SQL query'lerinin içinde belirttiğiniz table hint'lerinin SQL cümlelerinizde nasıl bir etki yarattığını inceleyeceğiz.

SQL Hint ve Query Optimizer

Temel olarak, SQL Server query processor tarafından yönetilen Execution Plan'inizin davranışını değiştiren anahtar kelimeler olarak düşünebiliriz. Table hint'ler, SQL Server Query Optimizer tarafıdan oluşturulan Execution Plan'ları ezmenize yardımcı olur.

Başlamadan önce bilmemiz gereken bir şey var: SQL Server Query Optimizer'ı oldukça "zeki" bir araç olarak düşünün. Size, yazdığınız her SQL cümlesi için en iyi Execution Plan'i oluşturur. Bundan dolayı, sadece gerekli olduğu zaman SQL cümlelerinizde Table Hint kullanmak en doğru tercih olacaktır. Yazdığınız table hint'in sistemde nasıl bir etkisi olacağından emin değilseniz, bırakın Query Optimizer yazdığınız sorguyu kendisi yorumlasın!

SQL Server Query Optimizer'ın tam olarak nasıl çalıştığnı merak ediyorsanız, Benjamin Navarez'in Simple Talk'daki bu makalesine bakmanızı öneririm.

 

Table Hint

Bir table hint, yani tablo ipucu kelimesi, tabolarınız için yazdığınız SQL cümlelerinin çalışmasında belirli bir locking, yani kilitleme mekanizması uygulamak istediğinizde kullanılan anahtar kelimelerdir. Unutmamak lazım ki, Query Optimizer, her zaman sorgunuz için en uygun locking anahtar kelimelerini kullanmaya çalışacaktır. Ancak bazı durumlar olabilir ki, SQL Server'ın size ürettiği yürütme planının dışında işlemler yapmak isteyebilirsiniz. Bu tür durumlarda tablo ipuçları kullanılabilir. Örnek verecek olursak, bir tablodan "full select" çektiğinizde ve kirli veri ile çalışmayı göze aldığınızda (NOLOCK) table hint'i kullanılabilir ve tablo üzerinde "blocking" yaratmamış oluruz.

Query Hint

Query ipuçları, ya da sorgu ipuçları, yazmış olduğunuz SQL sorgularına bir bütün olarak "locking" veya "davranışsal" mantık uygulamak istediğinizde kullanılır. Yazmış olduğunuz sorguların sonunda OPTION ile Query Analyzer'a bildirim yapılır ve belirttiğiniz özelliklere göre query execution plan'ı şekillendirilir.

Join Hint

Join Hint'leri, ya da birleştirme ipuçları, iki veya daha fazla tablonun birleştirildiği durumlarda kullanılır. Bu birleştirmelere INNER, OUTER, CROSS, LEFT, RIGHT gibi join tipleri dahildir.

 

Hint Kullanımı (Syntax)

WITH  ( <table_hint> [ [, ]...n ] )

<table_hint> ::= 
[ NOEXPAND ] { 
    INDEX  ( index_value [ ,...n ] ) 
  | INDEX =  ( index_value )    
  | FORCESEEK [( index_value ( index_column_name  [ ,... ] ) ) ]
  | FORCESCAN
  | FORCESEEK
  | HOLDLOCK 
  | NOLOCK 
  | NOWAIT
  | PAGLOCK 
  | READCOMMITTED 
  | READCOMMITTEDLOCK 
  | READPAST 
  | READUNCOMMITTED 
  | REPEATABLEREAD 
  | ROWLOCK 
  | SERIALIZABLE 
  | SNAPSHOT 
  | SPATIAL_WINDOW_MAX_CELLS = integer
  | TABLOCK 
  | TABLOCKX 
  | UPDLOCK 
  | XLOCK 

<table_hint_limited> ::=
{
    KEEPIDENTITY 
  | KEEPDEFAULTS 
  | HOLDLOCK 
  | IGNORE_CONSTRAINTS 
  | IGNORE_TRIGGERS 
  | NOLOCK 
  | NOWAIT
  | PAGLOCK 
  | READCOMMITTED 
  | READCOMMITTEDLOCK 
  | READPAST 
  | REPEATABLEREAD 
  | ROWLOCK 
  | SERIALIZABLE 
  | SNAPSHOT 
  | TABLOCK 
  | TABLOCKX 
  | UPDLOCK 
  | XLOCK 
}

 

Son olarak, birkaç table hint örneği verecek olursak;

SELECT * FROM dbo.Products WITH (NOLOCK)
WHERE ProductID = 12345

SELECT * FROM dbo.Shipments WITH (READCOMMITTEDLOCK)
WHERE ShipmentDate >= '2016-01-01 22:30:00:000'

UPDATE dbo.Products WITH (UPDLOCK) SET
CategoryID = 564651
WHERE ProductName LIKE '%food%'