Wenn ich auf SQL Server 2012 (11.0.6020) eine zugegebenermaßen recht einfache Testumgebung aufbaue, kann ich einen Plan mit zwei Hash-übereinstimmenden Abfragen neu erstellen, die über einen verkettet werden UNION ALL
. Mein Prüfstand zeigt nicht die falsche Schätzung an, die Sie sehen. Möglicherweise handelt es sich hierbei um ein SQL Server 2014 CE-Problem.
Ich erhalte eine Schätzung von 133,785 Zeilen für eine Abfrage, die tatsächlich 280 Zeilen zurückgibt. Dies ist jedoch zu erwarten, wie wir weiter unten sehen werden:
IF OBJECT_ID('dbo.Union1') IS NOT NULL
DROP TABLE dbo.Union1;
CREATE TABLE dbo.Union1
(
Union1_ID INT NOT NULL
CONSTRAINT PK_Union1
PRIMARY KEY CLUSTERED
IDENTITY(1,1)
, Union1_Text VARCHAR(255) NOT NULL
, Union1_ObjectID INT NOT NULL
);
IF OBJECT_ID('dbo.Union2') IS NOT NULL
DROP TABLE dbo.Union2;
CREATE TABLE dbo.Union2
(
Union2_ID INT NOT NULL
CONSTRAINT PK_Union2
PRIMARY KEY CLUSTERED
IDENTITY(2,2)
, Union2_Text VARCHAR(255) NOT NULL
, Union2_ObjectID INT NOT NULL
);
INSERT INTO dbo.Union1 (Union1_Text, Union1_ObjectID)
SELECT o.name, o.object_id
FROM sys.objects o;
INSERT INTO dbo.Union2 (Union2_Text, Union2_ObjectID)
SELECT o.name, o.object_id
FROM sys.objects o;
GO
SELECT *
FROM dbo.Union1 u1
INNER HASH JOIN sys.objects o ON u1.Union1_ObjectID = o.object_id
UNION ALL
SELECT *
FROM dbo.Union2 u2
INNER HASH JOIN sys.objects o ON u2.Union2_ObjectID = o.object_id;
Ich denke, der Grund liegt im Fehlen von Statistiken für die beiden resultierenden Verknüpfungen, die UNIONed sind. SQL Server muss in den meisten Fällen fundierte Vermutungen über die Selektivität von Spalten anstellen, wenn statistische Daten fehlen.
Joe Sack hat eine interessante Lektüre auf , dass hier .
Für a UNION ALL
ist es sicher zu sagen, dass wir genau die Gesamtzahl der von jeder Komponente der Union zurückgegebenen Zeilen sehen. Da SQL Server jedoch Zeilenschätzungen für die beiden Komponenten von verwendet UNION ALL
, werden die geschätzten Gesamtzeilen von beiden hinzugefügt Abfragen, um die Schätzung für den Verkettungsoperator zu erhalten.
In meinem obigen Beispiel beträgt die geschätzte Anzahl von Zeilen für jeden Teil von UNION ALL
66,8927, was summiert 133,785 entspricht, was wir für die geschätzte Anzahl von Zeilen für den Verkettungsoperator sehen.
Der tatsächliche Ausführungsplan für die obige Unionsabfrage sieht folgendermaßen aus:
Sie können die "geschätzte" vs "tatsächliche" Anzahl der Zeilen sehen. In meinem Fall entspricht das Hinzufügen der "geschätzten" Anzahl von Zeilen, die von den beiden Hash-Übereinstimmungsoperatoren zurückgegeben werden, genau der Menge, die vom Verkettungsoperator angezeigt wird.
Ich würde versuchen, eine Ausgabe von Trace 2363 usw. zu erhalten, wie in Paul Whites Beitrag empfohlen, den Sie in Ihrer Frage zeigen. Alternativ können Sie versuchen, OPTION (QUERYTRACEON 9481)
in der Abfrage auf die Version 70 CE zurückzukehren, um zu überprüfen, ob das Problem dadurch behoben wird.