http___programlamanotlari.blogspot.com__1.xml
1.1 2.1 3.1 3.2 4.1 5.1 6.1 6.2 6.3 7.1 8.1 8.2 9.1 10.1 11.1 11.2 12.1 12.2 13.1 13.2 14.1 14.2 15.1 16.1 17.1 17.2 18.1 18.2 19.1 19.2 20.1 21.1 22.1 23.1 24.1 24.2 25.1 26.1 27.1 27.2 28.1 29.1 30.1 30.2 31.1 31.2 32.1 33.1
http://weblogs.asp.net/arefin/archive/2010/05/04/returning-identity-value-in-sql-server-identity-vs-scope-identity-vs-ident-current.aspx: " We have some common misconceptions on returning the last inserted identity value from tables. To return the last inserted identity value we have options to use @@IDENTITY or SCOPE_IDENTITY or IDENT_CURRENT function depending on the requirement but it will be a real mess if anybody uses anyone of these functions without knowing exact purpose. So here I want to share my thoughts on this. @@IDENTITY, SCOPE_IDENTITY and IDENT_CURRENT are almost similar functions in terms of returning identity value. They all return values that are inserted into an identity column. Earlier in SQL Server 7 we used to use @@IDENTITY to return the last inserted identity value because those days we don’t have functions like SCOPE_IDENTITY or IDENT_CURRENT but now we have these three functions. So let’s check out which one responsible for what. IDENT_CURRENT returns the last inserted identity value in a particular table. It never depends on a connection or the scope of the insert statement. IDENT_CURRENT function takes a table name as parameter. Here is the syntax to get the last inserted identity value in a particular table using IDENT_CURRENT function. SELECT IDENT_CURRENT('Employee') in any table in the current session. But there is little difference between these two i.e. SCOPE_IDENTITY returns value inserted only within the current scope whereas @@IDENTITY is not limited to any particular scope. Here are the syntaxes to get the last inserted identity value using these functions SELECT @@IDENTITY SELECT SCOPE_IDENTITY() Employee and EmployeeLog. CREATE TABLE Employee ( EmpId NUMERIC(18, 0) IDENTITY(1,1) NOT NULL, EmpName VARCHAR(100) NOT NULL, EmpSal FLOAT NOT NULL, DateOfJoining DATETIME NOT NULL DEFAULT(GETDATE()) ) CREATE TABLE EmployeeLog ( EmpId NUMERIC(18, 0) IDENTITY(1,1) NOT NULL, EmpName VARCHAR(100) NOT NULL, EmpSal FLOAT NOT NULL, DateOfJoining DATETIME NOT NULL DEFAULT(GETDATE()) ) in the EmployeeLog whenever a record insert in the Employee table. So Suppose I insert a new record in the Employee table using following statement: INSERT INTO Employee (EmpName,EmpSal) VALUES ('Arefin','1') the scope of the insert statement and the trigger are different. In this situation if I retrieve last inserted identity value using @@IDENTITY, it will simply return the identity value from the EmployeeLog because it’s not limited to a particular scope. Now if I want to get the Employee table’s identity value then I need to use SCOPE_IDENTITY in this scenario. So the moral is always use SCOPE_IDENTITY to return the identity value of a recently created record in a sql statement or stored procedure. It’s safe and ensures bug free code.
1.1 2.1 3.1 4.1 5.1 6.1 7.1 8.1 9.1 10.1 11.1 12.1 13.1 14.1 15.1 16.1 17.1 18.1 19.1 20.1 21.1 22.1 23.1 24.1 25.1 26.1 27.1 28.1 29.1 30.1 31.1 32.1 33.1 34.1 35.1 36.1 37.1 38.1 39.1 40.1 41.1 42.1 43.1 44.1 45.1 46.1 47.1 48.1 49.1 50.1 51.1 52.1 53.1 54.1 55.1 56.1 57.1 58.1 59.1 60.1 61.1 62.1 63.1 64.1 65.1 66.1 67.1 68.1 69.1 70.1 71.1 72.1 73.1 74.1 75.1 76.1 77.1 78.1 79.1 80.1 81.1 82.1 83.1 84.1 85.1 86.1 87.1 88.1 89.1 90.1 91.1 92.1 93.1 94.1 95.1 96.1 97.1 98.1 99.1 100.1 101.1 102.1 103.1 104.1 105.1 106.1 107.1 108.1 109.1 110.1 111.1 112.1 113.1 114.1 115.1 116.1 117.1 118.1 119.1 120.1 121.1 122.1 123.1 124.1 125.1 126.1 127.1 128.1 129.1 130.1 131.1 132.1 133.1 134.1 135.1 136.1
4 Kasım 2010 Perşembe SQL Server Performansı için faydalı DMV(Dynamic Management View) ler Performans sıkıntısı oluşan sorguları bulmak ve SQL Server'ın performansını arttırmak için DMV lerden faydanılabilir. sys.dm_exec_requests, sys.dm_exec_sessions : Her iki view de server'da şu an çalışan istekleri getirir. Anlık olarak, uzun süren ve düşük performans gösteren sorguları bulmak için kullanılabilir. sys.dm_exec_query_stats : Çalışan sorguların cache planlarını getirir. sys.dm_exec_sql_text En kötü performanslı sorguyu tespit ettiğinizde, bu view i kullanarak sorgunun tam metnine ulaşabilirsiniz. DBCC INPUTBUFFER a benzer ve query handle parametresi alır. Query handle a sys.dm_exec_requests ve sys.dm_exec_query_stats view lerinde ulaşılabilir. sys.dm_os_wait_stats Server bazında bekleme istatistiklerini getirir ve dar boğazları tepit etmek için kullanılabilir. sys.dm_db_index_usage_stats Her bir indeksin kullanım istatistiklerini gösterir. Kullanılmayan ve az kullanılan indeksleri bulmak için kullanılabilir. Kullanılmayan indeklerin kaldırılması, veri güncelleme performansını arttırır, disk kullanımını azaltır. DMV ler, SQL server'ın son açılışından itibaren olan istatistikleri gösterir. sys.dm_db_missing_index_details Yeni indeks ihtiyacını tespit etmek için kullanılır. sys.dm_exec_requests, sys.dm_exec_sessions : Her iki view de server'da şu an çalışan istekleri getirir. Anlık olarak, uzun süren ve düşük performans gösteren sorguları bulmak için kullanılabilir. sys.dm_exec_query_stats : Çalışan sorguların cache planlarını getirir. sys.dm_exec_sql_text En kötü performanslı sorguyu tespit ettiğinizde, bu view i kullanarak sorgunun tam metnine ulaşabilirsiniz. DBCC INPUTBUFFER a benzer ve query handle parametresi alır. Query handle a sys.dm_exec_requests ve sys.dm_exec_query_stats view lerinde ulaşılabilir. sys.dm_os_wait_stats Server bazında bekleme istatistiklerini getirir ve dar boğazları tepit etmek için kullanılabilir. sys.dm_db_index_usage_stats Her bir indeksin kullanım istatistiklerini gösterir. Kullanılmayan ve az kullanılan indeksleri bulmak için kullanılabilir. Kullanılmayan indeklerin kaldırılması, veri güncelleme performansını arttırır, disk kullanımını azaltır. DMV ler, SQL server'ın son açılışından itibaren olan istatistikleri gösterir. sys.dm_db_missing_index_details Yeni indeks ihtiyacını tespit etmek için kullanılır. Etiketler: dmv, Performance, sql server 31 Ekim 2010 Pazar Partitioning Nedir? SQL Server'da partitioning yapısını, bir kitapevinde, birbirleriyle ilgili kitapları aynı raflara, ilgili olmayan kitapları farklı raflara koymaya benzetebiliriz. Romanlar bir rafa, Bilgisayar kitapları başka bir rafa gibi. Çok büyük bir tablomuz varsa, tablolarımızı bazı özelliklerine farklı partitionlara bölebilir ve performansımızı arttırabilir ve tablonun yönetemini kolaylaştırabiliriz. Örneğin bir satış tablosunu düşünün. Üzerinde binlerce kayıt olabilir. Ancak en çok bu yılın kayıtlarına bakar, diğer kayıtları daha az sorgularız. Sorgularımızda sql server'ın bir tablonun tüm kayıtlarını aramak yerine sadece daha az sayfayı taramasını, tabloyu bölerek sağlayabiliriz. Hatta eski kayıtlar ve yeni kayıtlar için farklı zamanlarda backup alabiliriz. Satırlara göre farklı bölümlere ayırmaya horizontal partitioning denir. Eğer bir tablo üzerinde çok sık kullandığımız kolonların yanında çok ender sorguladığımız kolonlar varsa, tabloyu kolonlara göre de bölümlere ayırabiliriz. Buna da vertical partioning denir. Bir tabloyu satırlardan ve sütünlardan oluşan bir yapı olarak düşünürsek, bu durumda tabloyu dikey olarak bölmüş oluruz. Vertical partioning ismi de buradan gelir. Çok büyük bir tablomuz varsa, tablolarımızı bazı özelliklerine farklı partitionlara bölebilir ve performansımızı arttırabilir ve tablonun yönetemini kolaylaştırabiliriz. Örneğin bir satış tablosunu düşünün. Üzerinde binlerce kayıt olabilir. Ancak en çok bu yılın kayıtlarına bakar, diğer kayıtları daha az sorgularız. Sorgularımızda sql server'ın bir tablonun tüm kayıtlarını aramak yerine sadece daha az sayfayı taramasını, tabloyu bölerek sağlayabiliriz. Hatta eski kayıtlar ve yeni kayıtlar için farklı zamanlarda backup alabiliriz. Satırlara göre farklı bölümlere ayırmaya horizontal partitioning denir. Eğer bir tablo üzerinde çok sık kullandığımız kolonların yanında çok ender sorguladığımız kolonlar varsa, tabloyu kolonlara göre de bölümlere ayırabiliriz. Buna da vertical partioning denir. Bir tabloyu satırlardan ve sütünlardan oluşan bir yapı olarak düşünürsek, bu durumda tabloyu dikey olarak bölmüş oluruz. Vertical partioning ismi de buradan gelir. Etiketler: partioning, sql server SQL Server da Index Türleri Index, SQL Server tablolarındaki verilere kolayca ulaşmamızı sağlayan yapılardır. Bir kitabın sonundaki indekse benzetilebilir. Hangi verinin nerede bulunduğu indeksler üzerinde tutulur. Temel olarak SQL Server'da iki tür indeks vardır. Clustered Index ve Nonclustered Indeks. Clustered Index, tablonun aynısıdır ve tablodaki tüm alanlar yer alır, sadece veriler, clustered indeks olarak tanımlanmış alanların sırasında tutulur, ancak nonclustered index'de sadece indeksteki veriler ve o verilerin nerede bulunduğuna dair işaretler tutulur. Üzerinde clustered indeks tanımlı olmayan tabloya heap tablo denir. Ve heap tablolarda veriler sıralı değildir. Üzerinde clustered indeks tanımlı olan bir tablonun iki versiyonu olur, heap orijinal tablodur ve bu tablonun sıralı hali de clustered indekste durur. Özel birşey söylenmezse, primary key yaratılırken, primary key alanına göre clustered indeks yaratılır. Bir tablo için sadece 1 tane clustered indeks yaratılabilir. Bu genel ayrımdan sonra içeriklerine göre indeksler aşağıdaki şekilde gruplandırılabilir. Simple Tek kolondan oluşan bir indekstir. Örneğin sadece ad kolonundan oluşan veya ad ve soyad birleşiminden oluşur. Compound 2 veya daha fazla kolondan oluşan indekstir. Unique Unique indeks olarak tanımlı alanlar için, aynı verilerden sadece bir tane girilmesine izin veren indeks türüdür. Temel olarak SQL Server'da iki tür indeks vardır. Clustered Index ve Nonclustered Indeks. Clustered Index, tablonun aynısıdır ve tablodaki tüm alanlar yer alır, sadece veriler, clustered indeks olarak tanımlanmış alanların sırasında tutulur, ancak nonclustered index'de sadece indeksteki veriler ve o verilerin nerede bulunduğuna dair işaretler tutulur. Üzerinde clustered indeks tanımlı olmayan tabloya heap tablo denir. Ve heap tablolarda veriler sıralı değildir. Üzerinde clustered indeks tanımlı olan bir tablonun iki versiyonu olur, heap orijinal tablodur ve bu tablonun sıralı hali de clustered indekste durur. Özel birşey söylenmezse, primary key yaratılırken, primary key alanına göre clustered indeks yaratılır. Bir tablo için sadece 1 tane clustered indeks yaratılabilir. Bu genel ayrımdan sonra içeriklerine göre indeksler aşağıdaki şekilde gruplandırılabilir. Simple Tek kolondan oluşan bir indekstir. Örneğin sadece ad kolonundan oluşan veya ad ve soyad birleşiminden oluşur. Compound 2 veya daha fazla kolondan oluşan indekstir. Unique Unique indeks olarak tanımlı alanlar için, aynı verilerden sadece bir tane girilmesine izin veren indeks türüdür. Etiketler: index, sql server 29 Ekim 2010 Cuma OUTPUT INTO OUTPUT INTO ile, UPDATE,INSERT,DELETE ve MERGE işlemleri sırasında etkilenen verileri bir tabloya kopyalayabiliriz. Log almak, son değişiklik yapılan verilen ile ilgili işlem yapmak için iyi bir yöntemdir. UPDATE Production.Product SET Color = 'blue' OUTPUT inserted.ProductID, inserted.Name, inserted.Color, deleted.Color INTO ProductLog WHERE ProductID= 134 inserted ve deleted sanal tabloları, trigger lardan bildiğimiz tabloların aynısıdır. Yeni değerler inserted tablosunda, eski değerler deleted tablosunda bulunur. INTO da verilen tablonun yapısı, OUTPUT da getirilen kolonlarla aynı yapıda olmalıdır. OUTPUT INTO da kullanılamayacak ifadeler UPDATE Production.Product SET Color = 'blue' OUTPUT inserted.ProductID, inserted.Name, inserted.Color, deleted.Color INTO ProductLog WHERE ProductID= 134 inserted ve deleted sanal tabloları, trigger lardan bildiğimiz tabloların aynısıdır. Yeni değerler inserted tablosunda, eski değerler deleted tablosunda bulunur. INTO da verilen tablonun yapısı, OUTPUT da getirilen kolonlarla aynı yapıda olmalıdır. OUTPUT INTO da kullanılamayacak ifadeler - Başka bir veri tabanından olan bir tablo - View - CTE (Common Table Expression) - Üzerine trigger yazılmış bir tablo - Foreign key constraint i tanımlı bir tablo - Merge veya Transaction replicationda yer alan bir tablo. DBCC CHECKIDENT DBCC CHECKIDENT (table_name, NORESEED | RESEED, [new_reseed_value]) DBCC CHECKIDENT ('myTableName',NORESEED) şeklinde çalıştırılsa, ilgili tablonun mevcut ve en yüksek identity değerini getirir. Eğer hatalı insert nedeniyle identity alanının değeri artmış, ancak tabloya yazılmamışsa bu tarz durumlar olabilir. Bu durumda DBCC CHECKIDENT, reseed parametresi ile çağrılarak, identity alanı istenilen değere geri çekilebilir. DBCC CHECKIDENT ('myTableName',RESEED, 50) ile identity değeri 50 ye alınır, bundan sonra oluşacak identity değerleri 51 den başlar. DBCC CHECKIDENT ('myTableName',RESEED) ise mevcut identity değerini maximum identity değeri ile eşitler. İçinde identity alanı olan bir tablonun içindeki tüm kayıtları sildiğinizde identity alanı sıfırlanmaz. Sıfırlanması için truncate table kullanabilirsiniz ancak tablo üzerinde foreign key ler tanımlı ise, truncate table kodu çalışmaz. Bu durumda tablodaki kayıtları sildikten sonra reseed ile identity alanını baştan başlatabilirsiniz. DBCC CHECKIDENT ('myTableName',NORESEED) şeklinde çalıştırılsa, ilgili tablonun mevcut ve en yüksek identity değerini getirir. Eğer hatalı insert nedeniyle identity alanının değeri artmış, ancak tabloya yazılmamışsa bu tarz durumlar olabilir. Bu durumda DBCC CHECKIDENT, reseed parametresi ile çağrılarak, identity alanı istenilen değere geri çekilebilir. DBCC CHECKIDENT ('myTableName',RESEED, 50) ile identity değeri 50 ye alınır, bundan sonra oluşacak identity değerleri 51 den başlar. DBCC CHECKIDENT ('myTableName',RESEED) ise mevcut identity değerini maximum identity değeri ile eşitler. İçinde identity alanı olan bir tablonun içindeki tüm kayıtları sildiğinizde identity alanı sıfırlanmaz. Sıfırlanması için truncate table kullanabilirsiniz ancak tablo üzerinde foreign key ler tanımlı ise, truncate table kodu çalışmaz. Bu durumda tablodaki kayıtları sildikten sonra reseed ile identity alanını baştan başlatabilirsiniz. Son eklenen kayıtda oluşan otomatik sayıyı öğrenmek CREATE TABLE Table1(ID int identity(1,1), Name nvarchar(50)) INSERT INTO @Table1(Name) VALUES('Test') SELECT @@IDENTITY , SCOPE_IDENTITY(), IDENT_CURRENT('Table1') Identity tanımlanmış bir alanı olan bir tabloya kayıt eklediğimizde, en son eklediğimiz kayıt ile birlikte oluşan Identity alanının değerini öğrenmek ihtiyacımız olduğunda 3 farklı yöntem kullanabiliriz. @@IDENTITY : Son oturumda oluşan son identity numarasını döndürür. Eğer bu tablo üzerinde bir trigger olsaydı ve trigger da üzerinde identity olan bir tabloya kayıt ekliyor olsaydı, @@Identity bize, Table1 tablosuna eklediğimiz kaydın identity değerini değil, trigger da kayıt eklenen tablonun identity değerini getirecekti. SCOPE_IDENTITY : Adından anlaşılacağı üzere, scope_identity fonksiyonu, mevcut oturumda ve mevcut kapsamda (scope) son oluşan identity değerini döndürür. Table1 üzerinde trigger olsa, ve başka bir identity alanı olan bir tabloya insert yapılsa bile, Table1 ile ilgili iş yaptığımız için, Table1 üzerinde oluşan son identity değerini bize verecektir. IDENT_CURRENT : Bu fonksiyon ise hem oturumdan, hem de kapsamdan bağımsız çalışır. Bu nedenle bir tablo adı parametresi ister. Verilen tabloda oluşmuş son identity değerini getirir. INSERT INTO @Table1(Name) VALUES('Test') SELECT @@IDENTITY , SCOPE_IDENTITY(), IDENT_CURRENT('Table1') Identity tanımlanmış bir alanı olan bir tabloya kayıt eklediğimizde, en son eklediğimiz kayıt ile birlikte oluşan Identity alanının değerini öğrenmek ihtiyacımız olduğunda 3 farklı yöntem kullanabiliriz. @@IDENTITY : Son oturumda oluşan son identity numarasını döndürür. Eğer bu tablo üzerinde bir trigger olsaydı ve trigger da üzerinde identity olan bir tabloya kayıt ekliyor olsaydı, @@Identity bize, Table1 tablosuna eklediğimiz kaydın identity değerini değil, trigger da kayıt eklenen tablonun identity değerini getirecekti. SCOPE_IDENTITY : Adından anlaşılacağı üzere, scope_identity fonksiyonu, mevcut oturumda ve mevcut kapsamda (scope) son oluşan identity değerini döndürür. Table1 üzerinde trigger olsa, ve başka bir identity alanı olan bir tabloya insert yapılsa bile, Table1 ile ilgili iş yaptığımız için, Table1 üzerinde oluşan son identity değerini bize verecektir. IDENT_CURRENT : Bu fonksiyon ise hem oturumdan, hem de kapsamdan bağımsız çalışır. Bu nedenle bir tablo adı parametresi ister. Verilen tabloda oluşmuş son identity değerini getirir. LOCK Türleri Veritabanında satır, sayfa veya tablo düzeyinde locklar oluşabilir. Bu locklar iki gruba ayrılırlar. Basic Locks : Shared Lock : Bir tablo üzerinde select sorgusu çalışırken oluşur. Bu lock, okuma yapacak diğer sorguların çalışmasına izin verir. Ancak shared lock çözülene kadar hiç bir transaction okunan kayıtları güncelleyemez. Update lock : Bir tablo üzerinde update işleri yapılırken oluşur. SQL Server, güncellenen verileri okumaya kalktığında kullanılır. Güncelleme sırasında, update lock, exclusive lock a dönüşür. Exclusive lock, birden fazla transaction ın aynı satırları güncellemeye çalışıp, deadlock oluşturmasını engeller. Exclusive lock : Diğer işlemlerin kilitlenmiş kaynaklara ulaşmasını engeller. Okuma işlemi sırasında, tabloda NOLOCK kullanıldıysa veya Isolation Level, READ UNCOMMITTED olarak ayarlandıysa, exclusive lock konulmuş olsa da veri okunur. Ancak diğer işlemler, exclusive lock kalkana kadar yapılamaz. Intent Lock : 6 farklı türde intent lock vardır. Intent shared (IS) lock istekleri veya shared lock ları korur. Bir kayıtda bir shared lock oluşmuş ise, ilgili kaydın bulunduğu page üzerinde intent shared lock oluşur. Intent exclusive (IX) lock Intent shared lock ın bir üstü seviyesidir. Bir kayıtda exclusive lock varsa, ilgili kaydın bulunduğu page üzerinde Intent Exclusive Lock konulur. Shared with intent exclusive (SIX) lock kilitleme hiyerarşisinde daha alt seviyede duran shared lock ları korur. Bir tabloda shared with intent exclusive lock oluşursa, değişiklik yapılan page üzerinde intent exclusive lock da yer alır. Intent update (IU) lock güncellenen tablonun bulunduğu pagelerdeki, shared ve istenilelen diğer lockları korur. Shared intent update lock, shared ve intent update locklarının birleşimininden oluşur. Bir transaction bir tablodan okuma yaptığında shared lock oluşur, daha sonra aynı transaction bir update işlemi yaparsa o zaman shared intent update lock a dönüşür. Bir tabloda select cümlesi çalıştırılırken, PAGLOCK hint i kullanılarak çekildiğinde de oluşan lock türüdür. Birbirini kapsayan birden fazla lock olmasının nedeni, SQL Server'ın aynı anda bir tablo üzerinde oluşan birçok lock yerine, tek bir lock ile çalışmasının daha verimli olmasındandır. Basic Locks : - S:Shared - U:Update - X:Exclusive - I : Intent - Sch: Schema - BU: Bulk Update - KR : Key Range Shared Lock : Bir tablo üzerinde select sorgusu çalışırken oluşur. Bu lock, okuma yapacak diğer sorguların çalışmasına izin verir. Ancak shared lock çözülene kadar hiç bir transaction okunan kayıtları güncelleyemez. Update lock : Bir tablo üzerinde update işleri yapılırken oluşur. SQL Server, güncellenen verileri okumaya kalktığında kullanılır. Güncelleme sırasında, update lock, exclusive lock a dönüşür. Exclusive lock, birden fazla transaction ın aynı satırları güncellemeye çalışıp, deadlock oluşturmasını engeller. Exclusive lock : Diğer işlemlerin kilitlenmiş kaynaklara ulaşmasını engeller. Okuma işlemi sırasında, tabloda NOLOCK kullanıldıysa veya Isolation Level, READ UNCOMMITTED olarak ayarlandıysa, exclusive lock konulmuş olsa da veri okunur. Ancak diğer işlemler, exclusive lock kalkana kadar yapılamaz. Intent Lock : 6 farklı türde intent lock vardır. Intent shared (IS) lock istekleri veya shared lock ları korur. Bir kayıtda bir shared lock oluşmuş ise, ilgili kaydın bulunduğu page üzerinde intent shared lock oluşur. Intent exclusive (IX) lock Intent shared lock ın bir üstü seviyesidir. Bir kayıtda exclusive lock varsa, ilgili kaydın bulunduğu page üzerinde Intent Exclusive Lock konulur. Shared with intent exclusive (SIX) lock kilitleme hiyerarşisinde daha alt seviyede duran shared lock ları korur. Bir tabloda shared with intent exclusive lock oluşursa, değişiklik yapılan page üzerinde intent exclusive lock da yer alır. Intent update (IU) lock güncellenen tablonun bulunduğu pagelerdeki, shared ve istenilelen diğer lockları korur. Shared intent update lock, shared ve intent update locklarının birleşimininden oluşur. Bir transaction bir tablodan okuma yaptığında shared lock oluşur, daha sonra aynı transaction bir update işlemi yaparsa o zaman shared intent update lock a dönüşür. Bir tabloda select cümlesi çalıştırılırken, PAGLOCK hint i kullanılarak çekildiğinde de oluşan lock türüdür. Birbirini kapsayan birden fazla lock olmasının nedeni, SQL Server'ın aynı anda bir tablo üzerinde oluşan birçok lock yerine, tek bir lock ile çalışmasının daha verimli olmasındandır. Etiketler: LOCK, sql server