Paging von SQL Server 2005-Ergebnissen
-
08-06-2019 - |
Frage
Wie kann ich Ergebnisse in SQL Server 2005 auslagern?
Ich habe es in SQL Server 2000 versucht, aber es gab keine zuverlässige Möglichkeit, dies zu tun.Ich frage mich jetzt, ob SQL Server 2005 über eine integrierte Methode verfügt.
Mit Paging meine ich beispielsweise, dass ich, wenn ich Benutzer nach ihrem Benutzernamen aufliste, nur die ersten 10 Datensätze zurückgeben möchte, dann die nächsten 10 Datensätze und so weiter.
Jede Hilfe wäre sehr dankbar.
Lösung
Sie können verwenden the Row_Number()
Funktion.Es wird wie folgt verwendet:
SELECT Row_Number() OVER(ORDER BY UserName) As RowID, UserFirstName, UserLastName
FROM Users
Daraus ergibt sich eine Ergebnismenge mit a RowID
Feld, zwischen dem Sie blättern können.
SELECT *
FROM
( SELECT Row_Number() OVER(ORDER BY UserName) As RowID, UserFirstName, UserLastName
FROM Users
) As RowResults
WHERE RowID Between 5 AND 10
usw
Andere Tipps
Wenn Sie versuchen, es in einer Anweisung zusammenzufassen (die Gesamtsumme plus die Seitenzahl).Möglicherweise müssen Sie die SQL Server-Unterstützung für die Partition by-Klausel (Fensterfunktionen in ANSI SQL-Begriffen) erkunden.In Oracle ist die Syntax genau wie im obigen Beispiel mit row_number(), aber ich habe auch eine Partition-by-Klausel hinzugefügt, um die Gesamtzahl der Zeilen zu erhalten, die in jeder Zeile enthalten sind, die im Paging zurückgegeben wird (die Gesamtzahl der Zeilen beträgt 1.262):
SELECT rn, total_rows, x.OWNER, x.object_name, x.object_type
FROM (SELECT COUNT (*) OVER (PARTITION BY owner) AS TOTAL_ROWS,
ROW_NUMBER () OVER (ORDER BY 1) AS rn, uo.*
FROM all_objects uo
WHERE owner = 'CSEIS') x
WHERE rn BETWEEN 6 AND 10
Beachten Sie, dass ich whereowner = 'CSEIS' habe und meine Partition nach dem Eigentümer liegt.Die Ergebnisse sind also:
RN TOTAL_ROWS OWNER OBJECT_NAME OBJECT_TYPE
6 1262 CSEIS CG$BDS_MODIFICATION_TYPES TRIGGER
7 1262 CSEIS CG$AUS_MODIFICATION_TYPES TRIGGER
8 1262 CSEIS CG$BDR_MODIFICATION_TYPES TRIGGER
9 1262 CSEIS CG$ADS_MODIFICATION_TYPES TRIGGER
10 1262 CSEIS CG$BIS_LANGUAGES TRIGGER
Die akzeptierte Antwort darauf funktioniert bei mir eigentlich nicht ... Ich musste noch einen Schritt weiter gehen, damit es funktionierte.
Als ich die Antwort versuchte
SELECT Row_Number() OVER(ORDER BY UserName) As RowID, UserFirstName, UserLastName
FROM Users
WHERE RowID Between 0 AND 9
Es schlug fehl und beschwerte sich, dass es nicht wisse, was RowID sei.
Ich musste es in eine innere Auswahl wie diese einpacken:
SELECT *
FROM
(SELECT
Row_Number() OVER(ORDER BY UserName) As RowID, UserFirstName, UserLastName
FROM Users
) innerSelect
WHERE RowID Between 0 AND 9
und dann hat es funktioniert.
Wenn ich Paging durchführen muss, verwende ich normalerweise auch eine temporäre Tabelle.Sie können einen Ausgabeparameter verwenden, um die Gesamtzahl der Datensätze zurückzugeben.Mit den Case-Anweisungen in der Auswahl können Sie die Daten nach bestimmten Spalten sortieren, ohne auf dynamisches SQL zurückgreifen zu müssen.
--Declaration--
--Variables
@StartIndex INT,
@PageSize INT,
@SortColumn VARCHAR(50),
@SortDirection CHAR(3),
@Results INT OUTPUT
--Statements--
SELECT @Results = COUNT(ID) FROM Customers
WHERE FirstName LIKE '%a%'
SET @StartIndex = @StartIndex - 1 --Either do this here or in code, but be consistent
CREATE TABLE #Page(ROW INT IDENTITY(1,1) NOT NULL, id INT, sorting_1 SQL_VARIANT, sorting_2 SQL_VARIANT)
INSERT INTO #Page(ID, sorting_1, sorting_2)
SELECT TOP (@StartIndex + @PageSize)
ID,
CASE
WHEN @SortColumn='FirstName' AND @SortDirection='ASC' THEN CAST(FirstName AS SQL_VARIANT)
WHEN @SortColumn='LastName' AND @SortDirection='ASC' THEN CAST(LastName AS SQL_VARIANT)
ELSE NULL
END AS sort_1,
CASE
WHEN @SortColumn='FirstName' AND @SortDirection='DES' THEN CAST(FirstName AS SQL_VARIANT)
WHEN @SortColumn='LastName' AND @SortDirection='DES' THEN CAST(LastName AS SQL_VARIANT)
ELSE NULL
END AS sort_2
FROM (
SELECT
CustomerId AS ID,
FirstName,
LastName
FROM Customers
WHERE
FirstName LIKE '%a%'
) C
ORDER BY sort_1 ASC, sort_2 DESC, ID ASC;
SELECT
ID,
Customers.FirstName,
Customers.LastName
FROM #Page
INNER JOIN Customers ON
ID = Customers.CustomerId
WHERE ROW > @StartIndex AND ROW <= (@StartIndex + @PageSize)
ORDER BY ROW ASC
DROP TABLE #Page
Ich glaube, Sie müssten eine separate Abfrage durchführen, um dies zu erreichen.
Ich konnte dies an meiner vorherigen Position mithilfe der Hilfe dieser Seite erreichen:Paging in DotNet 2.0
Sie haben auch eine separate Zählung der Zeilen.
Folgendes mache ich für das Paging:Alle meine großen Abfragen, die ausgelagert werden müssen, werden als Einfügungen in eine temporäre Tabelle codiert.Die temporäre Tabelle verfügt über ein Identitätsfeld, das sich ähnlich wie die oben erwähnte row_number() verhält.Ich speichere die Anzahl der Zeilen in der temporären Tabelle in einem Ausgabeparameter, damit der aufrufende Code weiß, wie viele Datensätze insgesamt vorhanden sind.Der aufrufende Code gibt außerdem an, welche Seite er haben möchte und wie viele Zeilen pro Seite aus der temporären Tabelle ausgewählt werden.
Das Coole an dieser Vorgehensweise ist, dass ich auch einen „Export“-Link habe, der es Ihnen ermöglicht, alle Zeilen aus dem Bericht als CSV über jedem Raster in meiner Anwendung zurückzugeben.Dieser Link verwendet dieselbe gespeicherte Prozedur:Sie geben einfach den Inhalt der temporären Tabelle zurück, anstatt die Paging-Logik auszuführen.Dies besänftigt Benutzer, die Paging hassen und es sehen möchten alles, und möchten es auf eine Million verschiedene Arten sortieren.