Úvod
Zobrazení na serveru SQL Server je struktura podobná virtuální tabulce založená na výsledné sadě příkazu SQL. Na povrchu je pohled podobný tabulce s podpisovou strukturou řádků a sloupců. Tyto řádky a sloupce však pocházejí z tabulek odkazovaných v dotazu, který definuje zobrazení.
Pohledy používáme k tomu, abychom se zaměřili na konkrétní sloupy pro účely, pro které jsou vytvořeny. Pohledy mohou sloužit také z bezpečnostních důvodů. Filtrují sloupce v podkladových tabulkách, které nechcete zviditelnit některým uživatelům. Zobrazuje sloupce filtrů jako klauzule WHERE filtruje řádky.
Dalším důvodem pro Views je jednoduchost. Seskupují sloupce z několika různých tabulek a vytvářejí obecný vzhled, který vypadá jako jedna tabulka.
Typy zobrazení
Základní uživatelsky definované pohledy lze snadno vytvořit. Proces je podobný psaní dotazů, které odkazují na jednu nebo více tabulek.
- Indexovaná zobrazení jsou zobrazení, která byla zhmotněna nebo uložena jako tabulka. Indexovaná zobrazení mohou zlepšit výkon dotazů, které agregují mnoho řádků. Nejsou však vhodné, pokud jsou podkladové tabulky často aktualizovány.
- Rozdělená zobrazení spojují horizontálně rozdělená data z tabulek lokálně (v rámci stejné instance) nebo napříč mnoha pomocí propojených serverů.
- Systémová zobrazení jsou běžné struktury, které SQL Server používá k vystavení metadat katalogu. Systémová zobrazení jsou většinou struktur, které se dotazují při odstraňování problémů s výkonem nebo zkoumání instance SQL Server.
Vytvoření pohledu z jedné tabulky
Podívejte se na příklad ve výpisu 1. První příkaz vrátí VŠECHNY záznamy v tabulce Purchasing.PurchaseOrders (1a), zatímco druhý dotaz vrátí pouze několik sloupců (1b).
Pomocí druhého dotazu můžeme vytvořit pohled, který vrátí stejnou sadu výsledků jako (1b). Když to uděláme, můžeme dotazovat pohled, abychom získali požadovaný výstup. Tím zjednodušujeme dotaz pro koncového uživatele.
-- Listing 1: Creating a Basic User-Defined View
-- 1a
SELECT * FROM
Purchasing.PurchaseOrders;
-- 1b
SELECT
PurchaseOrderID
, SupplierID
, OrderDate
, ExpectedDeliveryDate
FROM Purchasing.PurchaseOrders;
-- 1c
CREATE VIEW Purchasing.QuickOrders
AS
SELECT
PurchaseOrderID
, SupplierID
, OrderDate
, ExpectedDeliveryDate
FROM Purchasing.PurchaseOrders;
-- 1d
SELECT * FROM Purchasing.QuickOrders ;
Vytvoření pohledu ze dvou tabulek
Pomocí JOINů můžeme načíst data ze dvou nebo více tabulek, které mají vztah. Pomocí Views můžeme zjednodušit přístup k takovým datům.
Výpis 2 (2a) ukazuje JOIN mezi Purchasing.PurchaseOrders a Purchasing.PurchaseOrderLines. Z tohoto JOINu můžeme vytvořit pohled, který nám umožní získat stejná data pomocí dotazu, jak je uvedeno v (2c).
-- Listing 2: Creating a View from Two Tables
-- 2a
SELECT
po.PurchaseOrderID
, po.SupplierID
, po.OrderDate
, po.ExpectedDeliveryDate
, pol.Description
, pol.ExpectedUnitPricePerOuter
FROM Purchasing.PurchaseOrders po
INNER JOIN Purchasing.PurchaseOrderLines pol
ON po.PurchaseOrderID=pol.PurchaseOrderID;
-- 2b
CREATE VIEW Purchasing.DetailedOrders
AS
SELECT
po.PurchaseOrderID
, po.SupplierID
, po.OrderDate
, po.ExpectedDeliveryDate
, pol.Description
, pol.ExpectedUnitPricePerOuter
FROM Purchasing.PurchaseOrders po
INNER JOIN Purchasing.PurchaseOrderLines pol
ON po.PurchaseOrderID=pol.PurchaseOrderID;
-- 2c
SELECT * FROM Purchasing.DetailedOrders;
Vytvoření zobrazení napříč databázemi
Pomocí vícedílného pojmenování můžeme odkazovat na tabulky v jiné databázi. Proto můžeme provádět JOINy napříč databázemi a vytvářet pohledy, které zahrnují databáze. Je to užitečné pro určité aplikace, které šíří svá data napříč databázemi ve stejné instanci SQL Server.
Výpis 3 ukazuje podobný případ jako Výpis 2, ale s rozdílem:k dotazu JOIN přidáme třetí tabulku z jiné databáze. Všimněte si, že musíme použít LEFT OUTER JOIN, protože mezi tabulkami v obou databázích neexistuje žádný skutečný vztah. Zde jej používáme pouze pro ilustraci vytváření POHLEDU, které zahrnuje různé databáze.
Do příkazu CREATE VIEW jsme zavedli alias, protože máme sloupce ze dvou různých tabulek se stejným názvem. V takových případech musíme tyto sloupce rozlišovat.
-- Listing 3: Creating a View Across Databases
-- 3a
SELECT
po.PurchaseOrderID
,po.SupplierID
,po.OrderDate
,po.ExpectedDeliveryDate
,pol.Description
,pol.ExpectedUnitPricePerOuter
,so.orderid
,so.custid
,so.orderdate
FROM Purchasing.PurchaseOrders po
INNER JOIN Purchasing.PurchaseOrderLines pol
ON po.PurchaseOrderID=pol.PurchaseOrderID
LEFT OUTER JOIN TSQLV4.Sales.Orders so
ON po.PurchaseOrderID=so.orderid;
-- 3b
CREATE VIEW Purchasing.DetailedOrdersDistributed
AS
SELECT
po.PurchaseOrderID
,po.SupplierID
,po.OrderDate
,po.ExpectedDeliveryDate
,pol.Description
,pol.ExpectedUnitPricePerOuter
,so.orderid
,so.custid
,so.orderdate AS OrdersOrderDate
FROM Purchasing.PurchaseOrders po
INNER JOIN Purchasing.PurchaseOrderLines pol
ON po.PurchaseOrderID=pol.PurchaseOrderID
LEFT OUTER JOIN TSQLV4.Sales.Orders so
ON po.PurchaseOrderID=so.orderid;
-- 3c
SELECT * FROM Purchasing.DetailedOrdersDistributed;
Podívejte se na obrázek 1. Ukazuje výsledek provedení výpisu 3(3c). Všimněte si, že poslední tři sloupce jsou prázdné, protože TSQLV4.Sales.Orders tabulka nemá žádné řádky odpovídající podmínce JOIN.
Vytvoření zobrazení napříč instancemi
Poslední příkaz můžeme rozšířit zavedením tabulky, která žije úplně v jiné instanci.
Abychom toho dosáhli, musíme nejprve vytvořit Linked Server. Děláme to s kódem podobným tomu, který je uveden ve výpisu 4.
-- Listing 4: Linked Server
USE [master]
GO
EXEC master.dbo.sp_addlinkedserver @server = N'IGIRI01\SQLEXPRESS', @srvproduct=N'SQL Server'
EXEC master.dbo.sp_addlinkedsrvlogin @rmtsrvname=N'IGIRI01\SQLEXPRESS',@useself=N'True',@locallogin=NULL,@rmtuser=NULL,@rmtpassword=NULL
GO
Všimněte si, jak oslovujeme externí tabulku pomocí čtyřdílného názvu:
-- Listing 5: Creating a View Across Instances
-- 5a
CREATE VIEW Purchasing.DetailedOrdersExternal
AS
SELECT
po.PurchaseOrderID
,po.SupplierID
,po.OrderDate
,po.ExpectedDeliveryDate
,pol.Description
,pol.ExpectedUnitPricePerOuter
,ipol.StockItemID
,ipol.LastEditedWhen
FROM Purchasing.PurchaseOrders po
INNER JOIN Purchasing.PurchaseOrderLines pol
ON po.PurchaseOrderID=pol.PurchaseOrderID
INNER JOIN [IGIRI01\SQLEXPRESS].[WWI].[Purchasing].[PurchaseOrderLines] ipol
ON po.PurchaseOrderID=ipol.PurchaseOrderID;
-- 5b
SELECT * FROM Purchasing.DetailedOrdersExternal;
Zahrnutí funkcí do zobrazení
Vzhledem k tomu, že zobrazení jsou v podstatě dotazy, můžeme na ně aplikovat téměř cokoli, co děláme s běžnými dotazy. Můžeme zahrnout funkce, klauzule WHERE, výrazy CASE, aliasy atd.
Klauzule ORDER BY však není povolena, kromě toho, že používáte „hack TOP 100“. Výpisy 6 až 9 ilustrují použití těchto klauzulí v zobrazeních.
-- Listing 6: Creating a View with a Function
CREATE VIEW Purchasing.DetailedOrdersComplex
AS
SELECT
ipol.PurchaseOrderID
,ipol.Description
,ipol.ExpectedUnitPricePerOuter
,ipol.StockItemID
,CONVERT(VARCHAR, LastEditedWhen, 113) AS LastEditedLongDate
FROM [IGIRI01\SQLEXPRESS].[WWI].[Purchasing].[PurchaseOrderLines] ipol
-- Listing 7: Creating a View with a WHERE Clause
CREATE VIEW Purchasing.DetailedOrdersComplexFilt
AS
SELECT
ipol.PurchaseOrderID
,ipol.Description
,ipol.ExpectedUnitPricePerOuter
,ipol.StockItemID
,CONVERT(VARCHAR, LastEditedWhen, 113) AS LastEditedLongDate
FROM [IGIRI01\SQLEXPRESS].[WWI].[Purchasing].[PurchaseOrderLines] ipol
WHERE ipol.PurchaseOrderID<10;
-- Listing 8: Creating a View a TOP Clause
CREATE VIEW Purchasing.DetailedOrdersComplexTop
AS
SELECT TOP 10
ipol.PurchaseOrderID
,ipol.Description
,ipol.ExpectedUnitPricePerOuter
,ipol.StockItemID
,CONVERT(VARCHAR, LastEditedWhen, 113) AS LastEditedLongDate
FROM [IGIRI01\SQLEXPRESS].[WWI].[Purchasing].[PurchaseOrderLines] ipol
-- Listing 9: Creating a View with a CASE Expression
CREATE VIEW Purchasing.DetailedOrdersComplexTop
AS
SELECT TOP 10
CASE
ipol.PurchaseOrderID
WHEN 1 THEN 'First Order'
WHEN 2 THEN 'Second Order'
END PurchaseOrder
,ipol.Description
,ipol.ExpectedUnitPricePerOuter
,ipol.StockItemID
,CONVERT(VARCHAR, LastEditedWhen, 113) AS LastEditedLongDate
FROM [IGIRI01\SQLEXPRESS].[WWI].[Purchasing].[PurchaseOrderLines] ipol
Indexovaná zhlédnutí
Na indexovaná zobrazení jsme odkazovali dříve v článku. Indexovaná zobrazení mohou zlepšit výkon, s výjimkou případů, kdy jsou podkladové tabulky náročné na zápis. SQL Server vyžaduje, aby byly před vytvořením indexovaných zobrazení nebo provedením určitých operací na nich povoleny určité možnosti SET.
Klauzule WITH SCHEMABINDING by měla být použita při vytváření pohledu pro umístění indexu. Tato klauzule striktně spojuje pohled se základními objekty. Takové objekty tedy nelze zahodit.
-- Listing 10: Creating an Indexed View
SET ANSI_PADDING, ANSI_WARNINGS, CONCAT_NULL_YIELDS_NULL, ARITHABORT, QUOTED_IDENTIFIER, ANSI_NULLS ON;
CREATE VIEW Purchasing.DetailedOrdersIndexed
WITH SCHEMABINDING
AS
SELECT
po.PurchaseOrderID
,po.SupplierID
,po.OrderDate
,po.ExpectedDeliveryDate
FROM Purchasing.PurchaseOrders po;
CREATE UNIQUE CLUSTERED INDEX IX_ID
ON Purchasing.DetailedOrdersIndexed (PurchaseOrderID);
Závěr
V tomto článku jsme pohledy prozkoumali na určité úrovni podrobností. Stručně jsme probrali typy pohledů a uvedli několik příkladů uživatelsky definovaných pohledů a jak jsme použili JOINy k realizaci pohledů, které závisí na mnoha tabulkách. Zabývali jsme se také komplexními pohledy, které zahrnují funkce i indexovaná zobrazení.
Odkazy
- Zobrazení
- Indexovaná zhlédnutí
- Vytvářejte indexovaná zobrazení na serveru SQL Server