In-Memory örneği

Şunlar için geçerlidir: Azure SQL Veritabanı Azure SQL Yönetilen Örneği

Azure SQL Veritabanındaki In-Memory teknolojileri, uygulamanızın performansını artırmanıza ve veritabanınızın maliyetini azaltmanıza olanak tanır. Azure SQL Veritabanı'nda In-Memory teknolojileri kullanarak çeşitli iş yükleriyle performans geliştirmeleri elde edebilirsiniz.

Bu makalede, In-Memory OLTP kullanımını gösteren iki örnek ve Azure SQL Veritabanı'ndaki columnstore dizinlerini göreceksiniz.

Daha fazla bilgi için bkz.

 

1. In-Memory OLTP örneğini yükleyin

Azure portal birkaç tıklamayla AdventureWorksLT örnek veritabanını oluşturabilirsiniz. Ardından bu bölümdeki adımlarda AdventureWorksLT veritabanınızı OLTP nesneleriyle In-Memory nasıl zenginleştirebileceğiniz ve performans avantajlarını nasıl gösterebileceğiniz açıklanır.

In-Memory OLTP için daha basit ama görsel açıdan daha çekici bir performans tanıtımı için bkz:

Yükleme adımları

  1. Azure portal bir sunucuda Premium veya İş Açısından Kritik veritabanı oluşturun. Kaynak değerini AdventureWorksLT örnek veritabanı olarak ayarlayın. Ayrıntılı yönergeler için bkz. Azure SQL Veritabanında ilk veritabanınızı oluşturma.

  2. SQL Server Management Studio (SSMS.exe) ile veritabanına bağlanın.

  3. Bellek İçi OLTP Transact-SQL betiğini panonuza kopyalayın. T-SQL betiği, 1. adımda oluşturduğunuz AdventureWorksLT örnek veritabanında gerekli In-Memory nesnelerini oluşturur.

  4. T-SQL betiğini SSMS'ye yapıştırın ve betiği yürütün. MEMORY_OPTIMIZED = ON CREATE TABLE deyimleri yan tümcesi çok önemlidir. Örnek:

CREATE TABLE [SalesLT].[SalesOrderHeader_inmem](
    [SalesOrderID] int IDENTITY NOT NULL PRIMARY KEY NONCLUSTERED ...,
    ...
) WITH (MEMORY_OPTIMIZED = ON);

Hata 40536

T-SQL betiğini çalıştırdığınızda 40536 hatasını alırsanız, veritabanının Bellek İçi'yi destekleyip desteklemediğini doğrulamak için aşağıdaki T-SQL betiğini çalıştırın:

SELECT DatabasePropertyEx(DB_Name(), 'IsXTPSupported');

0 sonucunun olması In-Memory desteklenmediğini, 1 ise desteklendiği anlamına gelir. Sorunu tanılamak için veritabanının Premium hizmet katmanında olduğundan emin olun.

Oluşturulan bellek için iyileştirilmiş öğeler hakkında

Tablolar: Örnek, bellek için iyileştirilmiş aşağıdaki tabloları içerir:

  • SalesLT.Product_inmem
  • SalesLT.SalesOrderHeader_inmem
  • SalesLT.SalesOrderDetail_inmem
  • Demo.DemoSalesOrderHeaderSeed
  • Demo.DemoSalesOrderDetailSeed

Bellek için iyileştirilmiş tabloları SSMS'deki Nesne Gezgini inceleyebilirsiniz. Tablolar>Filtre Filtresi>Ayarları>Bellek için İyileştirilmiş'e sağ tıklayın. Değer 1'e eşittir.

Veya katalog görünümlerini sorgulayabilirsiniz, örneğin:

SELECT is_memory_optimized, name, type_desc, durability_desc
    FROM sys.tables
    WHERE is_memory_optimized = 1;

Yerel olarak derlenmiş saklı yordam: Katalog görünümü sorgusu aracılığıyla SalesLT.usp_InsertSalesOrder_inmem inceleyebilirsiniz:

SELECT uses_native_compilation, OBJECT_NAME(object_id), definition
    FROM sys.sql_modules
    WHERE uses_native_compilation = 1;

 

Örnek OLTP iş yükünü çalıştırma

Aşağıdaki iki saklı yordam arasındaki tek fark, ilk yordamın tabloların bellek için iyileştirilmiş sürümlerini, ikinci yordam ise normal disk içi tabloları kullanmasıdır:

  • SalesLT**. usp_InsertSalesOrder_inmem**
  • SalesLT**. usp_InsertSalesOrder_ondisk**

Bu bölümde, iki saklı yordamı stresli düzeylerde yürütmek için kullanışlı ostress.exe yardımcı programının nasıl kullanılacağını göreceksiniz. İki stres çalıştırmasının ne kadar sürdüğünü karşılaştırabilirsiniz.

ostress.exe çalıştırdığınızda, aşağıdakilerin her ikisi için de tasarlanmış parametre değerlerini geçirmenizi öneririz:

  • -n100 kullanarak çok sayıda eşzamanlı bağlantı çalıştırın.
  • -r500 kullanarak her bağlantı döngüsünü yüzlerce kez yapın.

Ancak, her şeyin çalıştığından emin olmak için -n10 ve -r50 gibi çok daha küçük değerlerle başlamak isteyebilirsiniz.

ostress.exe için betik

Bu bölümde, ostress.exe komut satırımıza eklenmiş olan T-SQL betiği görüntülenir. Betik, daha önce yüklediğiniz T-SQL betiği tarafından oluşturulan öğeleri kullanır.

Aşağıdaki betik, aşağıdaki bellek için iyileştirilmiş tablolara beş satır öğe içeren bir örnek satış siparişi ekler:

  • SalesLT.SalesOrderHeader_inmem
  • SalesLT.SalesOrderDetail_inmem
DECLARE
    @i int = 0,
    @od SalesLT.SalesOrderDetailType_inmem,
    @SalesOrderID int,
    @DueDate datetime2 = sysdatetime(),
    @CustomerID int = rand() * 8000,
    @BillToAddressID int = rand() * 10000,
    @ShipToAddressID int = rand() * 10000;

INSERT INTO @od
    SELECT OrderQty, ProductID
    FROM Demo.DemoSalesOrderDetailSeed
    WHERE OrderID= cast((rand()*60) as int);

WHILE (@i < 20)
begin;
    EXECUTE SalesLT.usp_InsertSalesOrder_inmem @SalesOrderID OUTPUT,
        @DueDate, @CustomerID, @BillToAddressID, @ShipToAddressID, @od;
    SET @i = @i + 1;
end

ostress.exe için önceki T-SQL betiğinin _ondisk sürümünü oluşturmak için, _inmem alt dizesinin her iki oluşumunu da _ondisk ile değiştirirsiniz. Bu değişiklikler tabloların ve saklı yordamların adlarını etkiler.

RML yardımcı programlarını yükleyin ve ostress

İdeal olarak, ostress.exe bir Azure sanal makinesinde (VM) çalıştırmayı planlıyorsunuz. AdventureWorksLT veritabanınızın bulunduğu Azure coğrafi bölgesinde bir Azure VM oluşturabilirsiniz. Ancak bunun yerine dizüstü bilgisayarınızda ostress.exe çalıştırabilirsiniz.

VM'ye veya seçtiğiniz herhangi bir konağa Yeniden Yürütme biçimlendirme dili (RML) yardımcı programlarını yükleyin. Yardımcı programlar ostress.exe içerir.

Daha fazla bilgi için bkz.

önce _inmem stres iş yükünü çalıştırın

ostress.exe komut satırımızı çalıştırmak için bir RML Cmd İstemi penceresi kullanabilirsiniz. Komut satırı parametreleri doğrudan ostress :

  • 100 bağlantıyı eşzamanlı olarak çalıştırın (-n100).
  • Her bağlantının T-SQL betiğini 50 kez çalıştırmasını sağlayın (-r50).
ostress.exe -n100 -r50 -S<servername>.database.windows.net -U<login> -P<password> -d<database> -q -Q"DECLARE @i int = 0, @od SalesLT.SalesOrderDetailType_inmem, @SalesOrderID int, @DueDate datetime2 = sysdatetime(), @CustomerID int = rand() * 8000, @BillToAddressID int = rand() * 10000, @ShipToAddressID int = rand()* 10000; INSERT INTO @od SELECT OrderQty, ProductID FROM Demo.DemoSalesOrderDetailSeed WHERE OrderID= cast((rand()*60) as int); WHILE (@i < 20) begin; EXECUTE SalesLT.usp_InsertSalesOrder_inmem @SalesOrderID OUTPUT, @DueDate, @CustomerID, @BillToAddressID, @ShipToAddressID, @od; set @i += 1; end"

Önceki ostress.exe komut satırını çalıştırmak için:

  1. Önceki çalıştırmalar tarafından eklenen tüm verileri silmek için SSMS'de aşağıdaki komutu çalıştırarak veritabanı veri içeriğini sıfırlayın:

    EXECUTE Demo.usp_DemoReset;
    
  2. Önceki ostress.exe komut satırının metnini panonuza kopyalayın.

  3. <placeholders>-S -U -P -d parametrelerini doğru gerçek değerlerle değiştirin.

  4. Düzenlenmiş komut satırınızı bir RML Cmd penceresinde çalıştırın.

Sonuç bir süredir

Tamamlandığında ostress.exe , çalıştırma süresini RML Cmd penceresinde çıktının son satırı olarak yazar. Örneğin, daha kısa bir test çalıştırması yaklaşık 1,5 dakika sürdü:

11/12/15 00:35:00.873 [0x000030A8] OSTRESS exiting normally, elapsed time: 00:01:31.867

sıfırlama, _ondisk için düzenleme ve yeniden çalıştırma

_inmem çalıştırmasının sonucunu elde ettikten sonra, _ondisk çalıştırması için aşağıdaki adımları gerçekleştirin:

  1. Önceki çalıştırma tarafından eklenen tüm verileri silmek için SSMS'de aşağıdaki komutu çalıştırarak veritabanını sıfırlayın:

    EXECUTE Demo.usp_DemoReset;
    
  2. tüm _inmem _ondisk ile değiştirmek için ostress.exe komut satırını düzenleyin.

  3. ostress.exe ikinci kez yeniden çalıştırın ve süre sonucunu yakalayın.

  4. Veritabanını yeniden sıfırlayın (büyük miktarda test verisi olabilecek verileri sorumlu bir şekilde silmek için).

Beklenen karşılaştırma sonuçları

In-Memory testlerimiz bu basit iş yükü için performansın dokuz kat arttığını ve veritabanıyla ostress aynı Azure bölgesindeki bir Azure VM üzerinde çalıştığını gösterdi.

 

2. In-Memory Analytics örneğini yükleyin

Bu bölümde, columnstore dizini kullanırken GÇ ve istatistik sonuçlarını geleneksel bir b ağacı diziniyle karşılaştıracaksınız.

OLTP iş yükünde gerçek zamanlı analiz için genellikle en iyisi kümelenmemiş columnstore dizini kullanmaktır. Ayrıntılar için bkz. Columnstore Dizinleri Açıklanan.

Columnstore analiz testini hazırlama

  1. Örnekten yeni bir AdventureWorksLT veritabanı oluşturmak için Azure portal kullanın.

    • Tam olarak bu adı kullanın.
    • Herhangi bir Premium hizmet katmanı seçin.
  2. sql_in-memory_analytics_sample panonuza kopyalayın.

    • T-SQL betiği, 1. adımda oluşturduğunuz AdventureWorksLT örnek veritabanında gerekli In-Memory nesnelerini oluşturur.
    • Betik, Boyut tablosunu ve iki olgu tablosunu oluşturur. Olgu tabloları her birinde 3,5 milyon satırla doldurulur.
    • Betiğin tamamlanması 15 dakika sürebilir.
  3. T-SQL betiğini SSMS'ye yapıştırın ve betiği yürütün. CREATE INDEX deyimindeki COLUMNSTORE anahtar sözcüğü aşağıdaki gibi çok önemlidir:
    CREATE NONCLUSTERED COLUMNSTORE INDEX ...;

  4. AdventureWorksLT'yi uyumluluk düzeyi 130 olarak ayarlayın:
    ALTER DATABASE AdventureworksLT SET compatibility_level = 130;

    Düzey 130, In-Memory özellikleriyle doğrudan ilgili değildir. Ancak düzey 130 genellikle 120'den daha hızlı sorgu performansı sağlar.

Anahtar tablolar ve columnstore dizinleri

  • Dbo. FactResellerSalesXL_CCI, veri düzeyinde gelişmiş sıkıştırmaya sahip kümelenmiş columnstore dizinine sahip bir tablodur.

  • Dbo. FactResellerSalesXL_PageCompressed, yalnızca sayfa düzeyinde sıkıştırılmış eşdeğer bir normal kümelenmiş dizine sahip bir tablodur.

Columnstore dizinini karşılaştırmak için anahtar sorgular

Performans geliştirmelerini görmek için çalıştırabileceğiniz birkaç T-SQL sorgu türü vardır. T-SQL betiğinin 2. adımında bu sorgu çiftine dikkat edin. Bunlar yalnızca bir satırda farklılık gösterir:

  • FROM FactResellerSalesXL_PageCompressed a
  • FROM FactResellerSalesXL_CCI a

Kümelenmiş columnstore dizini FactResellerSalesXL_CCI tablosundadır.

Aşağıdaki T-SQL betik alıntısı, her tablonun sorgusu için GÇ ve ZAMAN istatistiklerini yazdırır.

/*********************************************************************
Step 2 -- Overview
-- Page Compressed BTree table v/s Columnstore table performance differences
-- Enable actual Query Plan in order to see Plan differences when Executing
*/
-- Ensure Database is in 130 compatibility mode
ALTER DATABASE AdventureworksLT SET compatibility_level = 130
GO

-- Execute a typical query that joins the Fact Table with dimension tables
-- Note this query will run on the Page Compressed table, Note down the time
SET STATISTICS IO ON
SET STATISTICS TIME ON
GO

SELECT c.Year
    ,e.ProductCategoryKey
    ,FirstName + ' ' + LastName AS FullName
    ,count(SalesOrderNumber) AS NumSales
    ,sum(SalesAmount) AS TotalSalesAmt
    ,Avg(SalesAmount) AS AvgSalesAmt
    ,count(DISTINCT SalesOrderNumber) AS NumOrders
    ,count(DISTINCT a.CustomerKey) AS CountCustomers
FROM FactResellerSalesXL_PageCompressed a
INNER JOIN DimProduct b ON b.ProductKey = a.ProductKey
INNER JOIN DimCustomer d ON d.CustomerKey = a.CustomerKey
Inner JOIN DimProductSubCategory e on e.ProductSubcategoryKey = b.ProductSubcategoryKey
INNER JOIN DimDate c ON c.DateKey = a.OrderDateKey
GROUP BY e.ProductCategoryKey,c.Year,d.CustomerKey,d.FirstName,d.LastName
GO
SET STATISTICS IO OFF
SET STATISTICS TIME OFF
GO


-- This is the same Prior query on a table with a clustered columnstore index CCI
-- The comparison numbers are even more dramatic the larger the table is (this is an 11 million row table only)
SET STATISTICS IO ON
SET STATISTICS TIME ON
GO
SELECT c.Year
    ,e.ProductCategoryKey
    ,FirstName + ' ' + LastName AS FullName
    ,count(SalesOrderNumber) AS NumSales
    ,sum(SalesAmount) AS TotalSalesAmt
    ,Avg(SalesAmount) AS AvgSalesAmt
    ,count(DISTINCT SalesOrderNumber) AS NumOrders
    ,count(DISTINCT a.CustomerKey) AS CountCustomers
FROM FactResellerSalesXL_CCI a
INNER JOIN DimProduct b ON b.ProductKey = a.ProductKey
INNER JOIN DimCustomer d ON d.CustomerKey = a.CustomerKey
Inner JOIN DimProductSubCategory e on e.ProductSubcategoryKey = b.ProductSubcategoryKey
INNER JOIN DimDate c ON c.DateKey = a.OrderDateKey
GROUP BY e.ProductCategoryKey,c.Year,d.CustomerKey,d.FirstName,d.LastName
GO

SET STATISTICS IO OFF
SET STATISTICS TIME OFF
GO

P2 fiyatlandırma katmanına sahip bir veritabanında, geleneksel dizinle karşılaştırıldığında kümelenmiş columnstore dizinini kullanarak bu sorgu için yaklaşık dokuz kat daha fazla performans kazancı bekleyebilirsiniz. P15 ile columnstore dizinini kullanarak performans kazancının yaklaşık 57 katını elde edebilirsiniz.

Sonraki adımlar

Ek kaynaklar

Daha derin bilgiler

Uygulama tasarımı

Araçlar