I SQL, SUM()
funktion är en aggregerad funktion som returnerar summan av alla värden i ett givet uttryck.
Den kan också användas för att returnera summan av alla distinkta (unika) värden i ett uttryck.
Uttrycket måste vara numeriskt (det kan inte vara teckensträng, bitsträng eller datetime).
Nedan följer några grundläggande exempel för att visa hur det fungerar.
Exempeltabell
Anta att vi har följande tabell:
SELECT * FROM Products;
Resultat:
+-------------+------------+---------------------------------+----------------+-----------------------------------------+ | ProductId | VendorId | ProductName | ProductPrice | ProductDescription | |-------------+------------+---------------------------------+----------------+-----------------------------------------| | 1 | 1001 | Left handed screwdriver | 25.99 | Purple. Includes left handed carry box. | | 2 | 1001 | Long Weight (blue) | 14.75 | Includes a long wait. | | 3 | 1001 | Long Weight (green) | 11.99 | Approximate 30 minute waiting period. | | 4 | 1002 | Sledge Hammer | 33.49 | Wooden handle. Free wine glasses. | | 5 | 1003 | Chainsaw | 245.00 | Orange. Includes spare fingers. | | 6 | 1003 | Straw Dog Box | NULL | Tied with vines. Very chewable. | | 7 | 1004 | Bottomless Coffee Mugs (4 Pack) | 9.99 | Brown ceramic with solid handle. | | 8 | 1001 | Right handed screwdriver | 25.99 | Blue. Includes right handed carry box. | +-------------+------------+---------------------------------+----------------+-----------------------------------------+
Exempel
Vi kan använda följande fråga för att få summan av alla priser.
SELECT SUM(ProductPrice)
FROM Products;
Resultat:
+--------------------+ | (No column name) | |--------------------| | 367.20 | +--------------------+
I det här fallet lagras prisinformation i ProductPrice
kolumnen, och så skickar vi det som ett argument till SUM()
funktion, som sedan beräknar summan och returnerar resultatet.
Använda kolumnalias
Du kommer att märka att de tidigare resultaten inte innehåller ett kolumnnamn. Detta är att förvänta, eftersom SUM()
funktion returnerar inga kolumner. Du kan enkelt ange ett kolumnnamn genom att tilldela ett alias.
SELECT SUM(ProductPrice) AS Sum
FROM Products;
Resultat:
+--------+ | Sum | |--------| | 367.20 | +--------+
Filtrerade resultat
SUM()
funktionen fungerar på raderna som returneras av frågan. Så om du filtrerar resultaten blir resultatet av SUM()
kommer att återspegla det.
SELECT SUM(ProductPrice) AS Sum
FROM Products
WHERE VendorId = 1001;
Resultat:
+-------+ | Sum | |-------| | 78.72 | +-------+
I det här fallet är 78,72 summan av alla produkter som erbjuds av den angivna leverantören.
NULL
Värden
SUM()
funktionen ignorerar någon NULL
värden. I vår exempeltabell ovan, produktnummer 6
har NULL
i dess ProductPrice
kolumn, men det ignorerades i vår SUM()
exempel.
Beroende på ditt DBMS och dina inställningar kanske du ser en varning som NULL
värden eliminerades i resultatuppsättningen.
Här är ett exempel på vad du kan se:
SELECT SUM(ProductPrice) AS Sum
FROM Products;
Resultat:
+--------+ | Sum | |--------| | 367.20 | +--------+ Warning: Null value is eliminated by an aggregate or other SET operation.
Allt detta säger oss är att kolumnen innehöll minst en NULL
värde, och att det ignorerades vid beräkning av resultaten.
Datum/tiddata
SUM()
funktionen accepterar inte datum/tid uttryck.
Anta att vi har följande tabell:
SELECT PetName, DOB
FROM Pets;
Resultat:
+-----------+------------+ | PetName | DOB | |-----------+------------| | Fluffy | 2020-11-20 | | Fetch | 2019-08-16 | | Scratch | 2018-10-01 | | Wag | 2020-03-15 | | Tweet | 2020-11-28 | | Fluffy | 2020-09-17 | | Bark | NULL | | Meow | NULL | +-----------+------------+
Om vi försöker använda SUM()
på DOB
kolumnen får vi ett felmeddelande.
SELECT SUM(DOB) AS Sum
FROM Pets;
Resultat:
Msg 8117, Level 16, State 1, Line 1 Operand data type date is invalid for sum operator.
Teckendata
SUM()
funktion accepterar inte heller teckensträngsuttryck.
Här är vad som händer om vi försöker använda SUM()
på ProductName
kolumnen i våra Products
tabell (som använder en datatyp av varchar):
SELECT SUM(ProductName) AS Sum
FROM Products;
Resultat:
Msg 8117, Level 16, State 1, Line 1 Operand data type varchar is invalid for sum operator.
DISTINCT
Nyckelord
Du kan använda DISTINCT
nyckelord med SUM()
för att endast beräkna distinkta värden. Det vill säga, om det finns några dubbletter av värden, behandlas de som ett värde.
Exempel:
SELECT SUM(DISTINCT ProductPrice) AS DistinctSum
FROM Products;
Resultat:
+---------------+ | DistinctSum | |---------------| | 341.21 | +---------------+
Vi kan se att detta resultat är lägre än resultatet vi fick utan DISTINCT
nyckelord.
För att sammanfatta fick vi 367,20 utan DISTINCT
nyckelord och 341.21 med DISTINCT
nyckelord.
Detta beror på att det finns två artiklar som delar samma pris (vänsterskruvmejseln och högerskruvmejseln kostar båda 25,99). Därför är SUM()
funktion, när den används med DISTINCT
nyckelord, behandlar båda dessa värden som ett och beräknar resultatet därefter.
Fönsterfunktioner
Beroende på ditt DBMS kan du kanske använda en OVER
sats med din SUM()
funktion för att skapa en fönsterfunktion.
En fönsterfunktion utför en aggregatliknande operation på en uppsättning frågerader. Det ger ett resultat för varje frågerad. Detta till skillnad från en aggregerad operation, som grupperar frågerader i en enda resultatrad.
Här är ett exempel för att demonstrera konceptet.
Vi har redan sett Products
tabell. Vår databas har också en Customers
tabell och den innehåller följande data:
+--------------+----------------------+-------------------+------------+-----------------+------------+-----------+----------------+ | CustomerId | CustomerName | PostalAddress | City | StateProvince | ZipCode | Country | Phone | |--------------+----------------------+-------------------+------------+-----------------+------------+-----------+----------------+ | 1001 | Palm Pantry | 20 Esplanade | Townsville | QLD | 2040 | AUS | (308) 555-0100 | | 1002 | Tall Poppy | 12 Main Road | Columbus | OH | 43333 | USA | (310) 657-0134 | | 1003 | Crazy Critters | 10 Infinite Loops | Cairns | QLD | 4870 | AUS | (418) 555-0143 | | 1004 | Oops Media | 4 Beachside Drive | Perth | WA | 1234 | AUS | (405) 443-5987 | | 1005 | Strange Names Inc. | 789 George Street | Sydney | NSW | 2000 | AUD | (318) 777-0177 | | 1006 | Hi-Five Solutionists | 5 High Street | Highlands | HI | 1254 | AUS | (415) 413-5182 | +--------------+----------------------+-------------------+------------+-----------------+------------+-----------+----------------+
Vi kan hämta data från dessa tabeller och presentera dem som en resultatuppsättning genom att använda en join.
Vi kan också använda SUM()
funktion med OVER
sats för att tillämpa en fönsterfunktion på data.
SELECT
v.VendorName,
p.ProductName,
p.ProductPrice,
SUM(ProductPrice) OVER (PARTITION BY v.VendorName) AS "Sum For This Vendor"
FROM Products p
INNER JOIN Vendors v
ON v.VendorId = p.VendorId
ORDER BY VendorName, ProductPrice, "Sum For This Vendor";
Resultat:
+---------------+---------------------------------+----------------+-----------------------+ | VendorName | ProductName | ProductPrice | Sum For This Vendor | |---------------+---------------------------------+----------------+-----------------------| | Katty Kittens | Bottomless Coffee Mugs (4 Pack) | 9.99 | 9.99 | | Mars Supplies | Long Weight (green) | 11.99 | 78.72 | | Mars Supplies | Long Weight (blue) | 14.75 | 78.72 | | Mars Supplies | Right handed screwdriver | 25.99 | 78.72 | | Mars Supplies | Left handed screwdriver | 25.99 | 78.72 | | Pedal Medals | Straw Dog Box | NULL | 245.00 | | Pedal Medals | Chainsaw | 245.00 | 245.00 | | Randy Roofers | Sledge Hammer | 33.49 | 33.49 | +---------------+---------------------------------+----------------+-----------------------+
I det här fallet använde vi OVER
sats med vår SUM()
funktion för att partitionera resultatet efter leverantörsnamn.
Genom att göra detta kunde vi returnera prisinformation för varje produkt, såväl som summan av alla produkter från den givna leverantören. Summan ändras när leverantören ändras (såvida inte flera leverantörer råkar ha samma summa), men förblir densamma för alla produkter från samma leverantör.
Det här konceptet kan även tillämpas på andra aggregerade funktioner i SQL, såsom AVG()
, MIN()
, MAX()
, och COUNT()
.