laika222
10/31/2016 - 4:09 PM

Set Operators - UNION, UNION ALL, INTERSECT, EXCEPT

/************************
SET OPERATORS
************************/

/*
Set operators operate on two result sets, comparing complete rows between the results and then
returning certain rows into a final result set depending on the operator used.
The operators are UNION, UNION ALL, INTERSECT, and EXCEPT.

When using these, there are some rules:

1. The number of columns in the queries has to be the same, and the column data types must either be 
the same or be implicitly convertable.

2. The operations use distinctness-based comparisons and not equality based. Therefore, a comparison
between two NULLs yields true, and a comparison between a NULL and a non-NULL value yields false. This
is different than WHERE, ON and HAVING, which yield unknown when comparing a NULL with anything 
using both equality and inequality operators.

3. The operators are not cursor operators, and therefore the individual queries cannot have ORDER BY clauses.

4. However, you can have an ORDER BY clause at the end to determine the presentation of the final
result set.

5. The column names of the final result set are determined by the first query.

Set operators have precedence: INTERSECT precedes UNION and EXCEPT, and UNION and EXCEPT are evaluated
from left to right based on their position in the expression. However, you can always force precedence
by using parentheses.
*/


/************************
UNION AND UNION ALL
************************/


/*
UNION takes one result set and adds those rows to the rows of another result set. 
There are two main types: UNION, which de-dupes common values, and UNION ALL, which includes 
duplicates. If you complete a UNION, SQL Server will first combine the rows (same as UNION ALL), 
and it will then de-dup the list. Therefore, UNION ALL requires less work. If you know your result 
set does not have duplicates, then there are preformance benefits to using UNION ALL rather than UNION.

Some rules for using UNION:

1. Aliases must be in first query (before the UNION). All aliases in subsequent queries below the UNION are ignored.

2. Number of columns between the queries must be the same.

3. Data types must be compatible for implicit conversion (or converted explicitly)

*/

-- UNION
SELECT countryregion, city FROM HR.Employees
UNION
SELECT countryregion, city FROM Sales.Customers;

-- UNION ALL
SELECT countryregion, city FROM HR.Employees
UNION ALL
SELECT countryregion, city FROM Sales.Customers;

/************************
INTERSECT
************************/

/*

INTERSECT returns only distinct rows that appear in both sets being joined. In other words, if a
row appears at least once in the first set and at least once in the second set, it appears once in the
result of the INTERSECT OPERATOR.

*/

-- INTERSECT - combines multiple data sets but returns only distinct rows that appear in both result sets. Helps you find where there's duplication between the two result sets that are being UNIONed.
SELECT countryregion, city FROM HR.Employees
INTERSECT
SELECT countryregion, city FROM Sales.Customers;

/************************
EXCEPT
************************/

/*

EXCEPT peforms a set difference. It returns distinct rows that appear in the result of the first
query but not the second.

*/
-- EXCEPT - combines the sets and then only returns those rows that are NOT present in both sets (ie those rows that are in one or the other but not both). SELECT statement order is imported when using EXCEPT (figure this out).
SELECT countryregion, city FROM HR.Employees
EXCEPT
SELECT countryregion, city FROM Sales.Customers;