Sqlserver
 sql >> Datenbank >  >> RDS >> Sqlserver

Berechnen der laufenden Summe mit der OVER-Klausel und der PARTITION BY-Klausel in SQL Server

Sie stoßen häufig auf Szenarien, in denen Sie eine laufende Summe einer Menge berechnen müssen.

Eine laufende Summe bezieht sich auf die Summe der Werte in allen Zellen einer Spalte, die der nächsten Zelle in dieser bestimmten Spalte vorangeht.

Schauen wir uns ein Beispiel an, um dies klarer zu machen.

Wie Sie sehen können, enthält die dritte Zeile der Spalte RunningAgeTotal die Summe aller Werte in den Zeilen 1 bis 3 der Spalte StudentAge, d. h. 14 + 12 + 13 =39.

Ebenso ist der Wert der 4. Zeile der RunningAgeTotal-Spalte 49, was der Summe der Werte in den Zeilen 1 bis 4 der Spalte StudentAge entspricht.

In SQL Server kann die OVER-Klausel verwendet werden, um laufende Summen zu berechnen.

Lassen Sie uns anhand des folgenden Beispiels untersuchen, wie Sie dies verwenden können.

Einfaches Beispiel für die Berechnung der laufenden SQL-Summe

Lassen Sie uns einige Dummy-Daten erstellen, bevor wir tatsächlich eine Abfrage schreiben, die eine laufende Summe berechnet.

Führen Sie zuerst das folgende Skript aus:

CREATE DATABASE School
GO

USE School
GO

CREATE TABLE Students
(
	Id INT PRIMARY KEY IDENTITY,
	StudentName VARCHAR (50),
	StudentGender VARCHAR (50),
	StudentAge INT
)
GO

INSERT INTO Students VALUES ('Sally', 'Female', 14 )
INSERT INTO Students VALUES ('Edward', 'Male', 12 )
INSERT INTO Students VALUES ('Jon', 'Male', 13 )
INSERT INTO Students VALUES ('Liana', 'Female', 10 )
INSERT INTO Students VALUES ('Ben', 'Male', 11 )
INSERT INTO Students VALUES ('Elice', 'Female', 12 )
INSERT INTO Students VALUES ('Nick', 'Male', 9 )
INSERT INTO Students VALUES ('Josh', 'Male', 12 )
INSERT INTO Students VALUES ('Liza', 'Female', 10 )
INSERT INTO Students VALUES ('Wick', 'Male', 15 )

Dieses Skript erstellt die Students-Tabelle in der School-Datenbank. Die Tabelle enthält vier Spalten:Id, StudentName, StudentGender und Student. Die INSERT-Anweisung fügt der Datenbank 10 Dummy-Datensätze hinzu.

Um die laufende Summe von SQL zu berechnen, müssen wir eine OVER-Klausel verwenden und die Spalte hinzufügen, für die wir die laufende Summe berechnen möchten. Das folgende Skript berechnet die laufende Summe der Werte in der Spalte „StudentAge“ und fügt das Ergebnis der Spalte „RunningAgeTotal“ hinzu.

USE School
SELECT Id, StudentName, StudentGender, StudentAge,
SUM (StudentAge) OVER (ORDER BY Id) AS RunningAgeTotal
FROM Students

Im obigen Skript ruft die SELECT-Anweisung die Spalten „StudentName“, „StudentGender“ und „StudentAge“ zusammen mit der Spalte „Laufende Summe“ ab, d. h. „RunningAgeTotal“. Die SUM Aggregate-Funktion addiert die Werte zur Spalte StudentAge und die OVER-Klausel legt fest, dass die Addition in Form einer laufenden Summe ausgeführt werden soll, geordnet nach der Id-Spalte. Die Ausgabe des obigen Skripts sieht wie folgt aus:

Laufenden SQL-Durchschnitt berechnen

Sie können das Skript im letzten Abschnitt ändern, um ein laufendes Durchschnittsalter aller Schüler in der Tabelle „Studenten“ zu berechnen. Führen Sie dazu das folgende Skript aus:

USE School
SELECT Id, StudentName, StudentGender, StudentAge,
SUM (StudentAge) OVER (ORDER BY Id) AS RunningAgeTotal,
AVG (StudentAge) OVER (ORDER BY Id) AS RunningAgeAverage
FROM Students

Wie Sie sehen können, verwenden wir die Aggregatfunktion AVG, um das Durchschnittsalter aller Schüler in der Spalte StudentAge zu berechnen. Die Ausgabe des obigen Skripts sieht folgendermaßen aus:

Werfen Sie einen Blick auf die dritte Zeile der Spalte RunningAgeAverage. Sie enthält den Durchschnitt der Werte der Zeilen 1 bis 3 in der Spalte StudentAge, d. h. (14 + 12 + 13)/3 =13.

Aufteilen der laufenden Summe nach Spaltenwerten

Sie können auch eine laufende Summe berechnen, indem Sie die Daten nach den Werten in einer bestimmten Spalte partitionieren. Beispielsweise können Sie eine laufende SQL-Summe des Alters der Schüler berechnen, aufgeteilt nach Geschlecht. Dazu müssen Sie eine PARTITION BY-Anweisung zusammen mit der OVER-Klausel verwenden.

Sehen Sie sich das folgende Beispiel an:

USE School
SELECT Id, StudentName, StudentGender, StudentAge,
SUM (StudentAge) OVER (PARTITION BY StudentGender ORDER BY Id) AS RunningAgeTotal
FROM Students

Der einzige Unterschied zwischen der Berechnung der laufenden Summe für alle Datensätze und der Berechnung der laufenden Summe nach Geschlecht ist die Verwendung der PARTITION BY StudentGender-Klausel innerhalb der Klammer nach der OVER-Klausel. Das obige Skript berechnet die laufende Summe für die Werte in der Spalte StudentAge, partitioniert durch die Werte in der Spalte StudentGender. Die Ausgabe sieht so aus.

Sehen Sie sich nun die ersten vier Werte in der Spalte „RunningAgeTotal“ an (hervorgehoben durch das rote Rechteck). Diese Werte sind die laufende Summe der Studentinnen. In ähnlicher Weise enthalten die letzten 6 Zeilen (hervorgehoben durch das grüne Rechteck) eine laufende Gesamtsumme des Alters für die männlichen Schüler in der Schülertabelle.

Probleme mit OVER, wenn eine Spalte eine doppelte Spalte hat

Ein Problem tritt auf, wenn eine Spalte mit doppelten Werten mit einer OVER-Klausel verwendet wird, um eine laufende Summe zu berechnen. Werfen Sie einen Blick auf die Spalte StudentAge. Elice, Edward und Josh haben alle das gleiche Alter, d. h. 12. Ebenso haben Liana und Liza auch die gleichen Werte in der Spalte StudentAge, d. h. 10.

Wenn Sie versuchen, eine laufende Summe zu berechnen, indem Sie die Spalte StudentAge in der Klammer nach der OVER-Klausel angeben, werden Sie einige seltsame Ergebnisse sehen. Lassen Sie uns diese Abfrage ausführen:

USE School
SELECT Id, StudentName, StudentGender, StudentAge,
SUM (StudentAge) OVER (ORDER BY StudentAge) AS RunningAgeTotal
FROM Students

Die Ausgabe der obigen Abfrage lautet wie folgt:

In der zweiten Zeile der Spalte RunningAgeTotal ist der Wert 29. Er sollte jedoch 19 sein, da die Zeilen 1 und 2 der Spalte StudentAge 9 bzw. 10 enthalten. Da in diesem Fall sowohl die 2. als auch die 3. Zeile der Spalte „StudentAge“ einen doppelten Wert enthalten, d. h. 10, wird der Wert für die 2. Zeile der Spalte „RunningAgeTotal“ berechnet, indem 9, 10 und 10 addiert werden In der RunningAgeTotal-Spalte wird der Wert aus der zweiten Zeile, also 29, verwendet.

Wenn Sie sich die 5. Zeile der RunningAgeTotal-Spalte ansehen, ist der Wert 76. Eigentlich sollte es 40 + 12 =52 sein. Da jedoch die 5., 6. und 7. Zeile der StudentAge-Spalte doppelte Werte haben, d. h. 12, Die laufende Summe wird berechnet, indem 40 + 12 + 12 + 12 =76 addiert wird. Diese laufende Summe wurde für die Zeilen 6 und 7 der Spalte „RunningAgeTotal“ verwendet, da die Zeilen 6 und 7 der Spalte „StudentAge“ die doppelten Werte als Zeile enthalten 5.

Um diese Situation zu vermeiden, müssen Sie die Verwendung von Spalten mit doppelten Werten zusammen mit der OVER-Klausel beenden. Die Primärschlüsselspalte ist immer eine gute Wahl für die Verwendung mit der OVER-Klausel, da sie nur eindeutige Werte enthält.

Lesen Sie auch:

Gruppieren von Daten mit den Funktionen OVER und PARTITION BY

Lektionen zur Verwendung von OVER und PARTITION BY