SQL Server, arabellek önbelleğinde yeterli yer olmadığı bir sorgu için verileri nasıl işler?


10

Benim sorum, SQL Server, arabellek önbellek kullanılabilir alandan daha fazla veri hacmi çekmek için gereken bir sorguyu nasıl işler? Bu sorgu birden çok birleştirme içerdiğinden, sonuç kümesi zaten diskte bu biçimde mevcut değildir ve sonuçları derlemesi gerekir. Ancak derlemeden sonra bile, arabellek önbelleğinde mevcut olandan daha fazla alan gerektirir.

Bir örnek vereceğim. Toplam 6 GB Arabellek Önbellek alanı bulunan bir SQL Server örneğiniz olduğunu varsayalım. 7GB veri okuyan birden çok birleşim içeren bir sorgu çalıştırıyorum, SQL Server bu isteğe nasıl yanıt verebilir? Verileri geçici olarak tempdb'de saklıyor mu? Başarısız mı? Sadece diskten veri okuyan ve bir kerede segmentleri derleyen bir şey mi yapıyor?

Ayrıca, 7 GB toplam veri döndürmeye çalışıyorsam ne olur, bu SQL Server'ın işleme biçimini değiştirir mi?

Zaten bunu ele almak için çeşitli yolların farkındayım, sadece SQL Server belirtildiği gibi çalıştığında dahili olarak bu isteği nasıl işlediğini merak ediyorum.

Ayrıca, bu bilgilerin bir yerde var olduğundan eminim, ancak bulamamda başarısız oldum.


1
Layman'ın terimleriyle SQL Server, kendi dahili işlemenin çalışma tablolarını ve sonuçlarını tempdb'de saklayacaktır. Sayfalar gerektiğinde diskten okunur. Sayfalar zorlanana kadar veya SQL bunları diske vermeye hazır oluncaya kadar bellekte kalır. Bu büyük bir sorgu çalıştırdığınızda tempdb büyüyecektir. Sorguların dizlerine bir sistem getirdiğini gördüm, çünkü tempdb'nin kontrolsüz büyümesine izin verildi ve sürücüdeki kalan tüm alanı tüketti. Bunun% 100 doğru olmadığını biliyorum, sadece açıklamaya çalışıyorum. Verileri kullanan bölüm, söz konusu verilerin konumunu yöneten bölüm değildir
datagod

Yanıtlar:


13

Sayfalar gerektiği şekilde belleğe okunur, kullanılabilir boş bellek yoksa, değiştirilmemiş en eski sayfa gelen sayfa ile değiştirilir.

Bu, belleğe sığabileceğinden daha fazla veri gerektiren bir sorgu yürütürseniz, birçok sayfa bellekte çok kısa bir ömür yaşayacaktır ve bu da çok fazla G / Ç ile sonuçlanacaktır.

Bu etkiyi, Windows Performans İzleyicisi'ndeki "Sayfa Yaşam Beklentisi" sayacına bakarak görebilirsiniz. Bu sayaç hakkında harika ayrıntılar için https://sqlperformance.com/2014/10/sql-performance/knee-jerk-page-life-expectancy adresine bakın .

Yorumlarda, özellikle sorgunun sonuçları kullanılabilir arabellek alanından daha büyük olduğunda ne olacağını sordunuz . En basit örneği ele alalım, select * from some_very_big_table;- tablonun 32GB max server memory (MB)olduğunu ve 24GB olarak yapılandırıldığını varsayın . Tüm 32 GB tablo verileri, sayfa arabelleğindeki sayfalara teker teker okunacak, kilitlenecektir, ağ paketlerine biçimlendirilmiş ve kablo üzerinden gönderilmiştir. Bu sayfa sayfa gerçekleşir; aynı anda çalışan 300 sorguya sahip olabilirsiniz ve engelleme olmadıklarını varsayarsak, her sorguya ait veriler sayfa tampon alanına, her seferinde bir sayfaya okunacak ve müşteriye olabildiğince hızlı bir şekilde telin üzerine konulacaktır. veri isteyin ve tüketin. Her sayfadaki tüm veriler kabloya gönderildikten sonra, sayfa kilitlenmez ve çok hızlı bir şekilde diskteki başka bir sayfa ile değiştirilir.

Daha karmaşık bir sorgu durumunda, örneğin birkaç tablodan sonuçların toplanması durumunda, sayfalar sorgu işlemcisinin gerektirdiği gibi belleğe alınacaktır. Sorgu işlemcisi sonuçları hesaplamak için geçici bir çalışma alanına ihtiyaç duyarsa, sorgu için bir plan derlediğinde bunu önceden bilecek ve SQLOS'tan çalışma alanı (bellek) isteyecektir . SQLOS bir noktada ( zaman aşımına uğramadığı varsayılarak ) bu belleği sorgu işlemcisine verir ve bu noktada sorgu işlemeye devam edilir. Sorgu işlemcisi, SQLOS'tan ne kadar bellek isteneceğini tahmin ederken bir hata yaparsa, bir "diske dökülme" gerçekleştirmesi gerekebilirverinin geçici olarak geçici bir şekilde bir ara formda yazıldığı işlem. Tempdb'ye yazılan sayfalar, diğer sayfaların belleğe okunması için yer açmak üzere tempdb'ye yazıldıktan sonra açılır. Sonunda sorgulama işlemi, mandallama kullanılarak tamponda boş olarak işaretlenmiş sayfalara çağrılarak tempdb'de saklanan verilere dönecektir.

Şüphesiz yukarıdaki özette çok teknik detaylar bir yük eksik, ama SQL Server belleğe sığabilecek daha fazla veri nasıl işleyebilir özünü yakalar düşünüyorum.


Meraktan, ne tür bir sorgu 7GB veri çekiyor? Umarım bu bir toplu işlemdir.
datagod

Muhtemelen çok fazla değil ve haklısın, umarım bir toplu işlem olur. SQL'in bu isteği nasıl ele alacağını merak ettim
Dustin

5

Sorgunuzun tam olarak bu senaryoda ne yapacağını konuşamıyorum, ancak SQL Server'ın ne kadar gerekli olduğuna bağlı olarak birkaç seçeneği var.

  • Veriler TempDB'ye "dökülebilir", bu diskinizi kullanıyor olabilir
  • Eski sayfalar arabellek önbelleğinizden çıkarılabilir
  • SQL Server, önbelleği arabelleğe almak için bazı sayfaları yükleyebilir, kullanabilir, ardından yeni sayfaları

Ne olacağını bulmanın en iyi yolu, senaryoyu geliştirici bir ortamda oluşturmak ve bulmaktır.


2

Benim sorum, SQL Server, arabellek önbelleğine daha fazla veri hacmi çekmek için gereken bir sorguyu nasıl işliyorsa kullanılabilir alan var

Bu kısmı cevaplamak için size bunun nasıl yönetildiğini söyleyeyim. Sayfalar 8 KB boyutunda. Eğer büyük veri setini isteyen bir sorgu çalıştırmak ve edecektir bellek SQL Server getirilmesi için çok sayıda sayfaları gerektiren zaman değil tek seferde tüm sayfaları getirmek. Belirli sayfaları bulur ve tek tek 8 KB'lık sayfaları belleğe getirir ve ondan verileri okur ve sonucu verir ve bu şimdi devam edecek ve bu durumda belleğin daha az olduğu durumla karşı karşıya kaldığını varsayar. @Max gibi bir disk dikkat çekti. Doğru tahmin ettiğiniz gibi, bu düşük bellek işleri yavaşlatabilir, çünkü eski sayfaların kaldırılmasında biraz zaman harcanır. Burası kontrol noktası ve Lazywriterresme gelir. Lazywriter, bazı boş belleklerin diske yeni sayfalar getirmek için her zaman orada olduğundan emin olmaktır. Düşük boş arabellekle karşılaşıldığında tetiklenir ve yeni sayfalar olmak için boş alanlar oluşturur.

DÜZENLE

Bunu anlıyorum, ancak beni perdeleyen kısım, veriyi filtreliyorsanız \ bu verileri önbelleğin boyutunu aşarsanız ne olur.

Birleştirme ve filtreleme için bellek, sorgu çalışmadan önce kararlaştırılır ve gerçekten bir bellek çatışması olduğunu varsayar ve işlemi çalıştırmak için gereken bellek mevcut değildir SQL Server işlemcisi, "gerekli bellek"

Gerekli bellek: Sıralama ve karma birleştirmeyi çalıştırmak için gereken minimum bellek. Bu bellek kullanılabilir olmadan bir sorgu başlamayacağından gerekli olarak adlandırılır. SQL sunucusu, bu belleği sıralama ve karma birleştirmeyi işlemek için dahili veri yapıları oluşturmak üzere kullanır.

Bu yüzden en azından sorgu çalışmaya başlayacaktır, ancak çalışma zamanı sırasında ara sonucu Tempdb'ye dökülür ve yavaşlar. Sorgu Bellek Verimini Anlama'yı okumanızı kesinlikle öneririm


Bunu anlıyorum, ancak beni perdeleyen kısım, veriyi filtreliyorsanız \ bu verileri önbelleğin boyutunu aşarsanız ne olur. Dönüş kümesini üretmek için verilerin derlenmesi gerekir, ancak dönüş kümesi önbellek boyutundan daha büyüktür. Son sonucu üretene kadar sayfaları dahili olarak önbellekten geçiriyor mu? Benim düşüncem, önbelleği aştığı ve daha sonra diskten okuduğu için tempdb'ye sonuçları yazacağı olurdu, ancak durumun bu olup olmadığını bilmiyorum
Dustin

2
@Dustin Cevabımı düzenledi, lütfen kontrol edin
Shanky
Sitemizi kullandığınızda şunları okuyup anladığınızı kabul etmiş olursunuz: Çerez Politikası ve Gizlilik Politikası.
Licensed under cc by-sa 3.0 with attribution required.