sql >> Databasteknik >  >> RDS >> Sqlserver

Prestandaskillnad mellan vänsterfog och innerfog

Det finns minst ett fall där LEFT [OUTER] JOIN är ett bättre alternativ än [INNER] JOIN . Jag pratar om att få samma resultat med OUTER istället för INNER .

Exempel (jag använder AdventureWorks 2008-databas ):

-- Some metadata infos
SELECT  fk.is_not_trusted,  fk.name
FROM    sys.foreign_keys fk
WHERE   fk.parent_object_id=object_id('Sales.SalesOrderDetail');
GO

CREATE VIEW View1
AS 
SELECT  h.OrderDate, d.SalesOrderDetailID, o.ModifiedDate
FROM    Sales.SalesOrderDetail d
INNER JOIN Sales.SalesOrderHeader h ON d.SalesOrderID = h.SalesOrderID
INNER JOIN Sales.SpecialOfferProduct o ON d.SpecialOfferID=o.SpecialOfferID AND d.ProductID=o.ProductID;
GO

CREATE VIEW View2
AS
SELECT  h.OrderDate, d.SalesOrderDetailID, o.ModifiedDate
FROM    Sales.SalesOrderDetail d
INNER JOIN Sales.SalesOrderHeader h ON d.SalesOrderID = h.SalesOrderID
LEFT JOIN Sales.SpecialOfferProduct o ON d.SpecialOfferID=o.SpecialOfferID AND d.ProductID=o.ProductID;
GO

SELECT  SalesOrderDetailID
FROM    View1;

SELECT  SalesOrderDetailID
FROM    View2;

Resultat för den första frågan:

is_not_trusted name
-------------- ---------------------------------------------------------------
0              FK_SalesOrderDetail_SalesOrderHeader_SalesOrderID
0              FK_SalesOrderDetail_SpecialOfferProduct_SpecialOfferIDProductID

Utförandeplaner för de två senaste frågorna:

Anmärkning 1 / Visa 1: Om vi ​​tittar på exekveringsplanen för SELECT SalesOrderDetailID FROM View1 vi ser en FK-eliminering eftersom FK_SalesOrderDetail_SalesOrderHeader_SalesOrderID begränsningen är pålitlig och den har en enda kolumn. Men servern är tvingad (på grund av INNER JOIN Sales.SpecialOfferProduct ) för att läsa data från den tredje tabellen (SpecialOfferProduct) även SELECT/WHERE klausuler innehåller inga kolumner från den här tabellen och FK-begränsningen (FK_SalesOrderDetail_SpecialOfferProduct_SpecialOfferIDProductID) är (också) betrodd. Detta händer eftersom denna sista FK är flerkolumn.

Anmärkning 2 / Visa 2: Vad händer om vi vill ta bort den lästa (Scan /Seek ) på Sales.SpecialOfferProduct ? Denna andra FK är flerkolumn och för sådana fall kan SQL Server inte eliminera FK (se tidigare Conor Cunnigham blogginlägg). I det här fallet måste vi ersätta INNER JOIN Sales.SpecialOfferProduct med LEFT OUTER JOIN Sales.SpecialOfferProduct för att få FK eliminering. Båda SpecialOfferID och ProductID kolumner är NOT NULL och vi har en pålitlig FK som refererar till SpecialOfferProduct bord.



  1. node.js och mysql anslutningspool exporteras inte

  2. MySQL och PHP:UTF-8 med kyrilliska tecken

  3. Säkerhetskopiera/exportera en databas från SSH

  4. Datastruktur för olika turnerings-/tävlingstyper (liga, stege, enkel-/dubbeleliminering etc.)