Files
databases.softwareshinobi.com/landing/docs/SQL-101/017-having-clause_aggregate-functions.md
Software Shinobi caa5bbb983
All checks were successful
learn org at code.softwareshinobi.com/databases.softwareshinobi.com/pipeline/head This commit looks good
rewriting
2025-06-19 13:04:08 -04:00

220 lines
7.0 KiB
Markdown

# HAVING and Aggregate Functions
This document details the strategic application of the SQL `HAVING` clause and core aggregate functions. Mastery enables developers to write high-impact queries that efficiently process and filter grouped data, a critical requirement for performant applications.
Unlike the `WHERE` clause, which filters individual rows * before* grouping and aggregation, `HAVING` operates on grouped data *after* these operations have occurred. This distinction is fundamental for filtering based on aggregate results.
## Syntax
The `HAVING` clause is applied after `GROUP BY` and before `ORDER BY`.
```sql
SELECT column_name(s)
FROM table_name
WHERE condition -- Filters individual rows (optional)
GROUP BY column_name(s) -- Groups rows with identical values
HAVING condition -- Filters groups based on aggregate results
ORDER BY column_name(s); -- Sorts the final result set (optional)
```
The `HAVING` condition typically involves one or more aggregate functions and comparison/logical operators.
## Aggregate Functions
SQL aggregate functions transform a collection of values from multiple rows into a single summary value. They are indispensable for data analysis, reporting, and gaining insights from datasets. These functions operate on a set of values, not individual data points.
## Core Aggregate Functions
| Function | Description | Application |
| :------- | :----------------------------------------------------- | :-------------------------------------- |
| `AVG()` | Calculates the average value of a numeric column. | Mean purchase amount, average salary. |
| `SUM()` | Calculates the total sum of a numeric column. | Total revenue, sum of expenses. |
| `COUNT()`| Counts the number of rows or non-null values. | Total transactions, user signups. |
| `MAX()` | Returns the largest value in a column. | Highest price, maximum score. |
| `MIN() ` | Returns the smallest value in a column. | Lowest price, minimum score. |
Most aggregate functions disregard `NULL` values, with the exception of `COUNT(*)` which counts all rows regardless of `NULL` values.
## Aggregate Function Examples
Consider the following tables:
**Students**
| rollno | name | class |
| :----- | :---- | :---- |
| 1 | Troy | TE |
| 1 | Shree | BE |
| 2 | Harry | TE |
| 3 | John | TE |
| 3 | Shiv ani | TE |
**purchase**
| item | price | customer_name |
| :----------- | :---- | :------------ |
| Pen | 10 | Troy |
| Bag | 1000 | Troy |
| Vegetables | 500 | Troy |
| Shoes | 5000 | Troy |
| Water Bottle | 800 | XYZ |
| Mouse | 120 | ABC |
| Sun Glasses | 1350 | ABC |
## `AVG` function
Calculate the average purchase amount per customer.
```sql
SELECT AVG(price) AS Avg_Purchase, customer_name
FROM purchase
GROUP BY customer_name;
```
| Avg_Purchase | customer_name |
| :----------- | :------------ |
| 1 627.5000 | Troy |
| 800.0000 | XYZ |
| 735.0000 | ABC |
## `SUM` function
Calculate the total expenditure for each customer.
```sql
SELECT SUM(price) AS Total_Bill, customer_name
FROM purchase
GROUP BY customer_name;
```
| Total_Bill | customer_name |
| :--------- | :------------ |
| 6510 | Troy |
| 800 | XYZ |
| 1470 | ABC |
## `COUNT ` function
Determine the number of items purchased by each customer.
```sql
SELECT COUNT(item) AS Total_Items, customer_name
FROM purchase
GROUP BY customer_name;
```
| Total_Items | customer _name |
| :---------- | :------------ |
| 4 | Troy |
| 1 | XYZ |
| 2 | ABC |
## `MAX` function
Identify the highest single purchase value for each customer.
```sql
SELECT MAX(price) AS Highest_Purchase, customer_name
FROM purchase
GROUP BY customer_name;
```
| Highest_Purchase | customer_name |
| :--------------- | :------------ |
| 5000 | Troy |
| 800 | XYZ |
| 1350 | ABC |
## `MIN` function
Find the lowest single purchase value for each customer.
```sql
SELECT MIN(price) AS Lowest_Purchase, customer_name
FROM purchase
GROUP BY customer_name;
```
| Lowest_Purchase | customer_name |
| :-------------- | :------------ |
| 10 | Troy |
| 800 | XYZ |
| 120 | ABC |
## Having Clause Examples
These examples demonstrate using `HAVING` to filter results based on aggregate function output.
### Example 1: Filtering by Group Count
Identify classes with more than 2 students.
```sql
SELECT COUNT(class) AS strength, class
FROM Students
GROUP BY class
HAVING COUNT(class) > 2;
```
This query provides the count of students per class, filtered to include only those classes where the count exceeds 2.
| strength | class |
| :------- | :---- |
| 4 | TE |
### Example 2: Filtering by Minimum Aggregate Value
Find customers whose minimum purchase price is greater than 10.
```sql
SELECT customer_name, MIN(price) AS MIN_PURCHASE
FROM purchase
GROUP BY customer_name
HAVING MIN(price) > 10;
```
This query calculates the minimum purchase for each customer and includes only those customers where this minimum is above 10.
| customer_name | MIN_PURCHASE |
| :------------ | :----------- |
| XYZ | 800 |
| ABC | 120 |
### Example 3: Filtering and Ordering by Average Aggregate Value
List customers with an average purchase price greater than 550, ordered by name descending.
```sql
SELECT customer_name, AVG(price) AS Average_Purchase
FROM purchase
GROUP BY customer_name
HAVING AVG(price) > 550
ORDER BY customer_name DESC;
```
This query computes the average purchase price per customer, filters for averages above 550, and presents the results in descending order of customer name.
| customer_name | Average_Purchase |
| :------------ | :--------------- |
| XYZ | 800.0000 |
| Troy | 1627.5000 |
| ABC | 735.0000 |
### Example 4: Combining WHERE and HAVING
Calculate the total purchase amount for customers whose names start with "S" and whose total purchase exceeds 1000.
```sql
SELECT customer_name, SUM(price) AS Total_Purchase
FROM purchase
WHERE customer_ name LIKE "S%" -- WHERE filters rows before grouping
GROUP BY customer_name
HAVING SUM(price) > 1000; -- HAVING filters groups after aggregation
```
This query first filters rows to include only customers whose names start with 'S', then groups by customer name, calculates the total purchase, and finally filters these groups to include only those with a total exceeding 1000. Combining `WHERE` and `HAVING` allows for efficient multi -stage filtering.
| customer_name | Total_Purchase |
| :------------ | :------------- |
| Troy | 6510 |