Unterabfragen, die nur eine oder null Zeilen an die äußere Anweisung zurückgeben können, werden Einzeilen-Unterabfragen genannt. Einzeilen-Unterabfragen sind Unterabfragen, die mit einem Vergleichsoperator in einer WHERE- oder HAVING-Klausel verwendet werden.
Unterabfragen, die mehr als eine Zeile (aber nur eine Spalte) an die äußere Anweisung zurückgeben können, werden Mehrzeilen-Unterabfragen genannt. Mehrzeilen-Unterabfragen sind Unterabfragen, die in einer IN-, ANY- oder ALL-Klausel verwendet werden.
Sie speichern Produktinformationen in einer Tabelle namens "Products", und Informationen zu Bestellungen in der Tabelle "SalesOrdersItems". Die Tabelle "Products" enthält die Daten zu den einzelnen Produkten. Die Tabelle "SalesOrdersItems" enthält Daten zu den Bestellungen der Kunden. Wenn das Unternehmen Produkte nachbestellt, sobald der Lagerstand auf unter 50 Stück sinkt, kann die Frage "Welche Produkte sind unter dem Mindest-Lagerbestand?" mit folgender Abfrage beantwortet werden.
SELECT ID, Name, Description, Quantity FROM Products WHERE Quantity < 50; |
Ein zielführenderes Ergebnis allerdings würde berücksichtigen, wie häufig ein Produkt bestellt wird, weil ein geringer Lagerbestand bei häufig nachgefragten Produkten bedenklicher ist als bei solchen, die kaum bestellt werden.
Sie können eine Unterabfrage verwenden, um die durchschnittliche Anzahl von Artikeln zu ermitteln, die ein Kunde bestellt, und dann diesen Mittelwert in der Hauptabfrage verwenden, um Produkte zu finden, für die fast nur der Mindest-Lagerbestand vorhanden ist. Folgende Abfrage sucht die Namen und Beschreibungen der Produkte, deren Anzahl weniger als doppelt so hoch ist wie die durchschnittliche Anzahl der Artikel, die von einem Kunden bestellt werden.
SELECT Name, Description FROM Products WHERE Quantity < 2 * ( SELECT AVG( Quantity ) FROM SalesOrderItems ); |
In der WHERE-Klausel helfen Unterabfragen bei der Auswahl der im Abfrageergebnis anzuzeigenden Zeilen aus den Tabellen, die in der FROM-Klausel angegeben werden. In der HAVING-Klausel helfen Sie bei der Auswahl von Zeilengruppen, die von der GROUP BY-Klausel der Hauptabfrage angegeben wurden und in den Ergebnissen der Abfrage erscheinen sollen.
Das folgende Beispiel einer Einzeilen-Unterabfrage berechnet den durchschnittlichen Preis der Produkte in der Products-Tabelle. Der Mittelwert wird anschließend an die WHERE-Klausel der äußeren Abfrage übergeben. Die äußere Abfrage gibt ID, Name und UnitPrice aller Produkte zurück, die weniger teuer als der Mittelwert sind:
SELECT ID, Name, UnitPrice FROM Products WHERE UnitPrice < ( SELECT AVG( UnitPrice ) FROM Products ) ORDER BY UnitPrice DESC; |
ID | Name | UnitPrice |
---|---|---|
401 | Baseball Cap | 10.00 |
300 | Tee Shirt | 9.00 |
400 | Baseball Cap | 9.00 |
500 | Visor | 7.00 |
501 | Visor | 7.00 |
Angenommen, Sie wollen Artikel mit niedrigem Lagerbestand ermitteln und auch Bestellungen für diese Artikel erfassen. Sie könnten eine SELECT-Anweisung ausführen, die eine Unterabfrage in der WHERE-Klausel enthält, und zwar folgendermaßen:
SELECT * FROM SalesOrderItems WHERE ProductID IN ( SELECT ID FROM Products WHERE Quantity < 20 ) ORDER BY ShipDate DESC; |
In diesem Beispiel erstellt die Unterabfrage eine Liste aller Werte in der Spalte ID der Tabelle "Products", welche die Suchbedingung der WHERE-Klausel erfüllen. Die Unterabfrage gibt anschließend eine Reihe von Zeilen, aber nur eine einzige Spalte zurück. Das Schlüsselwort IN behandelt jeden Wert als Teil einer Menge und testet, ob jede Zeile in der Hauptabfrage Teil der Menge ist.
Zwei Tabellen in der SQL Anywhere-Beispieldatenbank enthalten Ergebnisse mit Finanzdaten. Bei der Tabelle "FinancialCodes" handelt es sich um eine Tabelle mit den verschiedenen Codes für Finanzdaten und deren Bedeutung. Um die Umsätze ("revenue") aus der Tabelle "FinancialData" aufzulisten, geben Sie Folgendes ein:
SELECT * FROM FinancialData WHERE Code IN ( SELECT Code FROM FinancialCodes WHERE type = 'revenue' ); |
Year | Quarter | Code | Amount |
---|---|---|---|
1999 | Q1 | r1 | 1023 |
1999 | Q2 | r1 | 2033 |
1999 | Q3 | r1 | 2998 |
1999 | Q4 | r1 | 3014 |
2000 | Q1 | r1 | 3114 |
... | ... | ... | ... |
Die Schlüsselwörter ANY und ALL können auf ähnliche Weise verwendet werden. Beispiel: Die folgende Abfrage liefert dieselben Ergebnisse wie die vorherige Abfrage, verwendet jedoch das Schlüsselwort ANY:
SELECT * FROM FinancialData WHERE FinancialData.Code = ANY ( SELECT FinancialCodes.Code FROM FinancialCodes WHERE type = 'revenue' ); |
Die Bedingung =ANY
ist identisch mit der IN-Bedingung. Darüber hinaus kann ANY aber auch mit Ungleichheits-Operatoren, wie z.B. <
oder >
verwendet werden, um Unterabfragen flexibler zu gestalten.
Das Schlüsselwort ALL ist ähnlich dem Wort ANY. Folgende Abfrage listet zum Beispiel Finanzdaten auf, bei denen es sich nicht um Umsätze handelt:
SELECT * FROM FinancialData WHERE FinancialData.Code <> ALL ( SELECT FinancialCodes.Code FROM FinancialCodes WHERE type = 'revenue' ); |
Dies entspricht der folgenden Anweisung mit NOT IN:
SELECT * FROM FinancialData WHERE FinancialData.Code NOT IN ( SELECT FinancialCodes.Code FROM FinancialCodes WHERE type = 'revenue' ); |
![]() |
Kommentieren Sie diese Seite in DocCommentXchange.
|
Copyright © 2012, iAnywhere Solutions, Inc. - SQL Anywhere 12.0.1 |