Операции над множествами: UNION, INTERSECT, EXCEPT
UNION, INTERSECT и EXCEPT комбинируют результаты двух запросов как множества.
UNION — объединение (строки из обоих, дубликаты убраны). INTERSECT — пересечение (строки, что есть в обоих). EXCEPT — разность (строки первого, которых нет во втором).
Условие применимости
Множественные операции склеивают результаты двух SELECT по вертикали. Требование: одинаковое число колонок и совместимые типы. Сопоставление идёт по позиции, а не по имени.
UNION: объединение без дубликатов
CREATE TABLE online(name TEXT);
INSERT INTO online VALUES ('Аня'),('Борис'),('Вика');
CREATE TABLE offline(name TEXT);
INSERT INTO offline VALUES ('Борис'),('Вика'),('Глеб');
SELECT name FROM online
UNION
SELECT name FROM offline
ORDER BY name;
Вывод:
name ----- Аня Борис Вика Глеб
Борис и Вика есть в обеих таблицах, но в результате по одному разу — UNION убирает дубликаты.
UNION vs UNION ALL
UNION отсеивает повторы — а для этого ему приходится сортировать/хешировать данные, что стоит ресурсов. UNION ALL просто склеивает результаты, не убирая дубли, и потому заметно быстрее. Если вы знаете, что пересечений нет (или дубли вам нужны), всегда берите UNION ALL.
SELECT 1 AS x
UNION ALL
SELECT 1
UNION ALL
SELECT 2;
Вывод:
x - 1 1 2
INTERSECT: пересечение
CREATE TABLE online(name TEXT);
INSERT INTO online VALUES ('Аня'),('Борис'),('Вика');
CREATE TABLE offline(name TEXT);
INSERT INTO offline VALUES ('Борис'),('Вика'),('Глеб');
SELECT name FROM online
INTERSECT
SELECT name FROM offline;
Вывод:
name ----- Борис Вика
Остались только те, кто есть и онлайн, и офлайн.
EXCEPT: разность
CREATE TABLE online(name TEXT);
INSERT INTO online VALUES ('Аня'),('Борис'),('Вика');
CREATE TABLE offline(name TEXT);
INSERT INTO offline VALUES ('Борис'),('Вика'),('Глеб');
SELECT name FROM online
EXCEPT
SELECT name FROM offline;
Вывод:
name ---- Аня
Аня есть онлайн, но нет офлайн. EXCEPT отвечает на вопрос «что есть только в первом наборе» — например, «какие товары были на складе вчера, но не сегодня».
Памятка
| Операция | Результат |
UNION | строки из обоих, дубли убраны |
UNION ALL | строки из обоих, дубли сохранены (быстрее) |
INTERSECT | строки, присутствующие в обоих |
EXCEPT | строки первого, которых нет во втором |
Итог
- Множественные операции требуют одинакового числа колонок и совпадения типов по позиции.
UNIONубирает дубли (дороже),UNION ALLих сохраняет (быстрее) — по умолчанию предпочитайте ALL, если дубли не страшны.INTERSECT— общее,EXCEPT— «есть в первом, нет во втором».