Leistungsproblem mit xpath in SQL Server 2008

7

Ich habe eine Tabelle mit vielen großen XML-Dokumenten.

Wenn ich xpath-Ausdrücke ausführe, um Daten aus diesen Dokumenten auszuwählen, tritt ein besonderes Leistungsproblem auf.

Meine Anfrage ist

SELECT
p.n.value('.', 'int') AS PurchaseOrderID
,x.ProductID 
FROM XmlLoadData x
CROSS APPLY x.PayLoad.nodes('declare namespace NS="http://schemas.datacontract.org/2004/07/XmlDbPerfTest"; 
/NS:ProductAndRelated[1]/NS:Product[1]/NS:PurchaseOrderDetails[1]/NS:PurchaseOrderDetail/NS:PurchaseOrderID[1]') p(n)

Die Abfrage dauert 2 Minuten und 8 Sekunden.

Wenn ich die [1]Teile der einzelnen Vorkommensknoten wie folgt entferne :

SELECT
p.n.value('.', 'int') AS PurchaseOrderID
,x.ProductID 
FROM XmlLoadData x
CROSS APPLY x.PayLoad.nodes('declare namespace NS="http://schemas.datacontract.org/2004/07/XmlDbPerfTest"; 
/NS:ProductAndRelated/NS:Product/NS:PurchaseOrderDetails/NS:PurchaseOrderDetail/NS:PurchaseOrderID') p(n)

Die Ausführungszeit sinkt auf nur 18 Sekunden.
Da die [1]-knoten in jedem übergeordneten Knoten in den Dokumenten nur einmal vorkommen, sind die Ergebnisse bis auf die Reihenfolge gleich.

Der tatsächliche Ausführungsplan für die erste (langsame) Abfrage lautet Plan für Abfrage 1

und die zweite (schnellere) Abfrage ist

Geben Sie hier die Bildbeschreibung ein

Abfrage 1 Vollbild Abfrage 2 Vollbild .

Soweit ich sehen kann, führt die Abfrage mit [1]dieselbe Ausführung aus wie die Abfrage ohne, jedoch mit einigen zusätzlichen Berechnungsschritten, um das erste Element zu finden.

Meine Frage ist, warum die zweite Abfrage schneller ist.
Ich hätte erwartet, dass die Ausführung der Abfrage mit [1]vorzeitig unterbrochen wird , wenn eine Übereinstimmung gefunden wird, und somit die Ausführungszeit anstelle des Gegenteils verkürzt.
Gibt es Gründe, warum die Ausführung nicht vorzeitig unterbrochen wird [1]und somit die Ausführungszeit verkürzt wird?

Das ist mein Tisch

CREATE TABLE [dbo].[XmlLoadData](
    [ProductID] [int] NOT NULL,
    [PayLoad] [xml] NOT NULL,
    [Size]  AS (len(CONVERT([nvarchar](max),[PayLoad],0))),
 CONSTRAINT [PK_XmlLoadData] PRIMARY KEY CLUSTERED 
(
    [ProductID] ASC
)WITH (PAD_INDEX  = OFF, STATISTICS_NORECOMPUTE  = OFF, 
       IGNORE_DUP_KEY = OFF, ALLOW_ROW_LOCKS  = ON, 
       ALLOW_PAGE_LOCKS  = ON) ON [PRIMARY]
) ON [PRIMARY]

Bearbeiten:
Leistungszahlen aus SQL Profiler:

Abfrage 1:

CPU     Reads   Writes  Duration 
126251  1224892 0       129797

Abfrage 2:

CPU     Reads   Writes  Duration 
50124   612499  0       16307
Albin Sunnanbo
quelle
1
Bitte posten Sie kein Bild des Ausführungsplans, sondern den Plan . Bedeutet die XML-Datei. Es gibt eine Menge von Informationen in diesen XML - Dateien , die nicht in dem Bild des Plans angezeigt wird.
Remus Rusanu

Antworten:

2

Die zweite Abfrage verwendet Parallelität. Das heißt, es war teuer genug für den Optimierer, die Augen vor dem zusätzlichen Aufwand zu verschließen.

Ich denke, die zweite Abfrage weist den Optimierer an, "alles zu sichern", was mit einem parallelen Scan durchgeführt wird. SQL Server möchte auf Anfrage auf diese Weise "alles sichern".
Während die erste Abfrage nach "analysieren und dann etwas geben" fragt. Der Optimierer kann ohnehin nicht wissen, dass es nur einen Knoten gibt, daher ist der Ausführungsplan, den er letztendlich auswählt, sehr unterschiedlich.

Ich würde sagen, es ähnelt einer Situation, in der ein Tabellenscan billiger ist als viele Indexsuchen.

GSerg
quelle
Sie haben Recht, dass die zweite Abfrage Parallelität verwendet. Aber ich kann nicht herausfinden, wie das zu einem so großen Unterschied auf meiner Quad-Core-Maschine führen könnte. Ich habe die Frage mit Zahlen aus dem SQL-Profiler bearbeitet. Die gesamte CPU-Zeit, die für die zweite Abfrage aufgewendet wird, ist ohnehin um mehr als 50% geringer. Ist der verringerte CPU-Verbrauch ein Effekt davon, dass der parallele Abfrageplan nicht nur parallel, sondern auch effizienter ist?
Albin Sunnanbo
1

Sehen Sie sich die Leistungsoptimierungen für den XML-Datentyp in SQL Server 2005 und den Abschnitt "Verschieben von Ordnungszahlen an das Ende von Pfaden" an.

Ordnungszahlen, die in Pfadausdrücken für die Korrektheit des statischen Typs verwendet werden, sind gute Kandidaten für die Platzierung am Ende von Pfadausdrücken. Der Pfadausdruck /book[1]/title[1]entspricht, (/book/title)[1]wenn jedes <book>Element untergeordnete Elemente hat <title>. Letzteres kann sowohl für den XML-indizierten Fall als auch für den XML-Blob-Fall schneller ausgewertet werden, indem das erste <title>Element unter einem <book>Element in der Dokumentreihenfolge bestimmt wird. In ähnlicher Weise führt der Pfadausdruck zu einer (/book/@ISBN)[1]schnelleren Ausführung als /book[1]/@ISBN.

Mikael Eriksson
quelle
0

Das Abfragen von XML ist ein Biest. Das Hinzufügen von XML-Indizes zu Ihrer Tabelle beschleunigt die Abfragen erheblich.

mrdenny
quelle
Ich habe vor, diese Abfragen einmal auszuführen, um relationale Tabellen mit den Daten zu erstellen, nach denen ich suchen möchte. Der Grund, warum ich Geschwindigkeit brauche, ist, dass wir die Störungen in unserer Produktionsdatenbank minimieren möchten, wenn wir die Daten extrahieren. Das Erstellen eines XML-Index nimmt ebenfalls viel Zeit in Anspruch.
Albin Sunnanbo