Database
 sql >> Database >  >> RDS >> Database

SQL AVG() per principianti

In SQL, il AVG() function è una funzione aggregata che restituisce la media di tutti i valori in una determinata espressione.

Può anche essere utilizzato per restituire la media di tutti i valori distinti (unici) in un'espressione.

L'espressione deve essere numerica (non può essere stringa di caratteri, stringa di bit o data/ora).

Di seguito sono riportati alcuni esempi di base per dimostrare come funziona.

Tabella di esempio

Supponiamo di avere la seguente tabella:

SELECT * FROM Products;

Risultato:

+-------------+------------+---------------------------------+----------------+-----------------------------------------+
| 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.  |
+-------------+------------+---------------------------------+----------------+-----------------------------------------+

Esempio

Possiamo utilizzare la seguente query per ottenere la media di tutti i prezzi.

SELECT AVG(ProductPrice)
FROM Products;

Risultato:

+--------------------+
| (No column name)   |
|--------------------|
| 52.457142          |
+--------------------+

In questo caso, le informazioni sul prezzo sono memorizzate nel ProductPrice colonna, e quindi lo passiamo come argomento a AVG() funzione, che quindi calcola la media e restituisce il risultato.

Utilizzo degli alias di colonna

Noterai che i risultati precedenti non includono un nome di colonna. Questo è prevedibile, perché AVG() la funzione non restituisce alcuna colonna. Puoi facilmente fornire un nome di colonna assegnando un alias.

SELECT AVG(ProductPrice) AS Average
FROM Products;

Risultato:

+-----------+
| Average   |
|-----------|
| 52.457142 |
+-----------+

Risultati filtrati

Il AVG() La funzione opera sulle righe restituite dalla query. Quindi, se filtri i risultati, il risultato di AVG() lo rifletterà.

SELECT AVG(ProductPrice) AS Average
FROM Products
WHERE VendorId = 1001;

Risultato:

+-----------+
| Average   |
|-----------|
| 19.680000 |
+-----------+

In questo caso, 19,680000 è il prezzo medio di tutti i prodotti offerti dal venditore specificato.

NULL Valori

Il AVG() la funzione ignora qualsiasi NULL valori. Nella nostra tabella di esempio sopra, il numero del prodotto 6 ha NULL nel suo ProductPrice colonna, ma è stata ignorata nel nostro AVG() esempio.

A seconda del tuo DBMS e delle tue impostazioni, potresti visualizzare o meno un avviso che NULL i valori sono stati eliminati nel set di risultati.

Ecco un esempio di ciò che potresti vedere:

SELECT AVG(ProductPrice) AS Average
FROM Products;

Risultato:

+-----------+
| Average   |
|-----------|
| 52.457142 |
+-----------+
Warning: Null value is eliminated by an aggregate or other SET operation.

Tutto questo ci dice è che la colonna conteneva almeno un NULL valore e che è stato ignorato durante il calcolo dei risultati.

Dati data/ora

Il AVG() la funzione non accetta espressioni di data/ora.

Supponiamo di avere la seguente tabella:

SELECT PetName, DOB 
FROM Pets;

Risultato:

+-----------+------------+
| 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       |
+-----------+------------+

Se proviamo a utilizzare AVG() sul DOB colonna, riceveremo un errore.

SELECT AVG(DOB) AS Average
FROM Pets;

Risultato:

Msg 8117, Level 16, State 1, Line 1
Operand data type date is invalid for avg operator.

Dati sui caratteri

Il AVG() anche la funzione non accetta espressioni di stringhe di caratteri.

Ecco cosa succede se proviamo a utilizzare AVG() nel ProductName colonna dei nostri Products tabella (che utilizza un tipo di dati varchar):

SELECT AVG(ProductName) AS Average
FROM Products;

Risultato:

Msg 8117, Level 16, State 1, Line 1
Operand data type varchar is invalid for avg operator.

Il DISTINCT Parola chiave

Puoi usare il DISTINCT parola chiave con AVG() calcolare solo valori distinti. Cioè, se sono presenti valori duplicati, vengono trattati come un valore.

Esempio:

SELECT AVG(DISTINCT ProductPrice) AS DistinctAverage
FROM Products;

Risultato:

+-------------------+
| DistinctAverage   |
|-------------------|
| 56.868333         |
+-------------------+

Possiamo vedere che questo risultato è maggiore del risultato che abbiamo ottenuto senza il DISTINCT parola chiave.

Per ricapitolare, abbiamo ottenuto 52.457142 senza il DISTINCT parola chiave e 56.868333 con il DISTINCT parola chiave.

Questo perché ci sono due articoli che condividono lo stesso prezzo (il cacciavite sinistro e il cacciavite destro hanno entrambi un prezzo di 25,99). Pertanto, il AVG() funzione, se usata con DISTINCT parola chiave, tratta entrambi i valori come uno e calcola il risultato di conseguenza.

Funzioni della finestra

A seconda del tuo DBMS, potresti essere in grado di utilizzare un OVER clausola con il tuo AVG() funzione per creare una funzione finestra.

Una funzione finestra esegue un'operazione di tipo aggregato su un insieme di righe di query. Produce un risultato per ogni riga di query. Ciò è in contrasto con un'operazione di aggregazione, che raggruppa le righe di query in un'unica riga di risultati.

Ecco un esempio per dimostrare il concetto.

Abbiamo già visto i Products tavolo. Il nostro database ha anche un Customers tabella e contiene i seguenti dati:

+--------------+----------------------+-------------------+------------+-----------------+------------+-----------+----------------+
| 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 |
+--------------+----------------------+-------------------+------------+-----------------+------------+-----------+----------------+

Possiamo recuperare i dati da queste tabelle e presentarli come un set di risultati utilizzando un join.

Possiamo anche usare AVG() funzione con il OVER clausola per applicare una funzione finestra ai dati.

SELECT 
    v.VendorName,
    p.ProductName,
    p.ProductPrice,
    AVG(ProductPrice) OVER (PARTITION BY v.VendorName) AS "Average For This Vendor"
FROM Products p 
INNER JOIN Vendors v 
ON v.VendorId = p.VendorId
ORDER BY VendorName, ProductPrice, "Average For This Vendor";

Risultato:

+---------------+---------------------------------+----------------+---------------------------+
| VendorName    | ProductName                     | ProductPrice   | Average For This Vendor   |
|---------------+---------------------------------+----------------+---------------------------|
| Katty Kittens | Bottomless Coffee Mugs (4 Pack) | 9.99           | 9.990000                  |
| Mars Supplies | Long Weight (green)             | 11.99          | 19.680000                 |
| Mars Supplies | Long Weight (blue)              | 14.75          | 19.680000                 |
| Mars Supplies | Right handed screwdriver        | 25.99          | 19.680000                 |
| Mars Supplies | Left handed screwdriver         | 25.99          | 19.680000                 |
| Pedal Medals  | Straw Dog Box                   | NULL           | 245.000000                |
| Pedal Medals  | Chainsaw                        | 245.00         | 245.000000                |
| Randy Roofers | Sledge Hammer                   | 33.49          | 33.490000                 |
+---------------+---------------------------------+----------------+---------------------------+

In questo caso abbiamo usato il OVER clausola con il nostro AVG() funzione per partizionare il risultato in base al nome del fornitore.

In questo modo, siamo stati in grado di restituire le informazioni sui prezzi per ciascun prodotto, nonché il prezzo medio di tutti i prodotti di quel determinato fornitore. Il prezzo medio cambia al variare del fornitore (a meno che più fornitori non abbiano la stessa media), ma rimane lo stesso per tutti i prodotti dello stesso fornitore.

Questo concetto può essere applicato anche ad altre funzioni aggregate in SQL, come SUM() , MIN() , MAX() e COUNT() .