Как применять оператор SQL UNION для объединения результатов запросов
Оператор языка SQL UNION предназначен для объединения результирующих таблиц базы данных, полученных с применением слова SELECT. Условие объединения результирующих таблиц: совпадение числа, порядка следования и типа данных столбцов. ORDER BY следует применять к результату объединения и размещать только в конце составного запроса. Оператор UNION имеет следующий синтаксис:
SELECT ИМЕНА_СТОЛБЦОВ (1..N) FROM ИМЯ_ТАБЛИЦЫ UNION SELECT ИМЕНА_СТОЛБЦОВ (1..N) FROM ИМЯ_ТАБЛИЦЫ
В этой конструкции объединяемые запросы могут иметь условия в секции WHERE, а могут не иметь их. При помощи оператора UNION можно объединить запросы на извлечение данных как из одной таблицы, так и из разных.
При использовании оператора UNION без слова ALL результат не содержит дубликатов, а со словом ALL — содержит дубликаты.
Итоги и индивидуальные значения в одной таблице с помощью оператора SQL UNION
Одним запросом можно вывести из таблицы индивидуальные значения столбцов, например, число лет, проработанных сотрудниками фирмы, размеры их заработной платы и другие. Другим запросом — с использованием агрегатных функций — можно получить, например, сумму заработных плат, получаемых сотрудниками отделов или занимающих те или иные должности, или среднее число лет трудового стажа (в таких запросах применяется группировка с помощью оператора GROUP BY).
А если нам требуется получить в одной таблице и сводку всех индивидуальных значений, и итоговые значения? Здесь на помощь приходит оператор SQL UNION, с помощью которого два запроса объединяются. К результату объединения требуется применить упорядочение, используя оператор ORDER BY. Для чего это необходимо, будет лучше понятно из примеров.
Если вы хотите выполнить запросы к базе данных из этого урока на MS SQL Server, но эта СУБД не установлена на вашем компьютере, то ее можно установить, пользуясь инструкцией по этой ссылке.
Пример 1. В базе данных фирмы есть таблица Staff, содержащая данные о сотрудниках фирмы. В ней есть столбцы Salary (размер заработной платы), Job (должность) и Years (длительность трудового стажа). Первый запрос возвращает индивидуальные размеры заработной платы, упорядоченные по должностям:
SELECT Name, Job, Salary FROM STAFF ORDER BY Job
Результатом выполнения запроса будет следующая таблица:
| Name | Job | Salary |
| Sanders | Mgr | 18357.5 |
| Marenghi | Mgr | 17506.8 |
| Pernal | Sales | 18171.2 |
| Doctor | Sales | 12322.4 |
| Factor | Sales | 16228.7 |
Второй запрос вернёт суммарную заработную плату по должностям. Мы уже готовим этот запрос для соединения с первым, поэтому будем помнить, что условием соединения является равное число столбцов, совпадение их названий, порядка следования и типов данных. Поэтому включаем в таблицу с итогами также столбец Name с произвольным значением ‘Z-TOTAL’:
SELECT ‘Z-TOTAL’ AS Name, Job, SUM (Salary) AS Salary FROM STAFF GROUP BY Job
Результатом выполнения запроса будет следующая таблица:
| Name | Job | Salary |
| Z-TOTAL | Mgr | 35864.3 |
| Z-TOTAL | Sales | 46722.3 |
Теперь объединим запросы при помощи оператора UNION и применим оператору ORDER BY к результату объединения. Группировать следует по двум столбцам: должность (Job) и имя (Name), чтобы строки с итоговыми (суммарными) значениями, в которых значение имени — ‘Z-TOTAL’, находились ниже строк с индивидуальными значениями. Объединение результатов запросов будет следующим:
( SELECT Name, Job, Salary FROM STAFF ) UNION ( SELECT ‘Z-TOTAL’ AS Name, Job, SUM (Salary) AS Salary FROM STAFF GROUP BY Job) ORDER BY Job, Name
Результатом выполнения запроса с оператором UNION будет следующая таблица, в которой каждая первая строка в каждой группе должностей будет содержать суммарную заработную плату сотрудников, работающих на этой должности:
| Name | Job | Salary |
| Marenghi | Mgr | 17506.8 |
| Sanders | Mgr | 18357.5 |
| Z-TOTAL | Mgr | 35864.3 |
| Doctor | Sales | 12322.4 |
| Factor | Sales | 16228.7 |
| Pernal | Sales | 18171.2 |
| Z-TOTAL | Sales | 46722.3 |
Написать запросы с использованием UNION самостоятельно, а затем посмотреть решение
Пример 2. Данные — те же, что в примере 1, но задача немного посложнее. Требуется вывести в одной таблице не только индивидуальные размеры заработной платы, упорядоченные по должностям и суммарную заработную плату по должностям, но суммарную заработную плату по всем сотрудникам.
Пример 3. В базе данных фирмы есть таблица Staff, содержащая данные о сотрудниках фирмы. В ней есть столбцы Name (фамилия), Dept (номер отдела), и Years (длительность трудового стажа).
| Name | Dept | Years |
| Sanders | 20 | 7 |
| Pernal | 20 | 8 |
| Marenghi | 38 | 5 |
| Doctor | 20 | 5 |
| Factor | 38 | 8 |
Вывести в одной таблице средний трудовой стаж по отделам и индивидуальные значения длительности трудового стажа сотрудников, сгруппированных по номерам отделов.
Другие случаи объединения запросов к одной таблице с помощью оператора SQL UNION
Пример 4. В базе данных фирмы есть таблица Staff, содержащая данные о сотрудниках фирмы. В ней есть столбцы Salary (размер заработной платы), Job (должность) и Years (длительность трудового стажа). Первый запрос нужен для получения данных о сотрудниках, заработная плата которых более 21000:
SELECT ID, Name FROM STAFF WHERE SALARY > 21000
Результатом выполнения запроса будет следующая таблица:
| ID | Name |
| 140 | Fraye |
| 160 | Molinare |
| 260 | Jones |
Второй запрос возвращает имена сотрудников, должность которых «менеждер», а число лет трудового стажа — менее 8:
SELECT ID, Name FROM STAFF WHERE Job = ‘Mgr’ AND Years ORDER BY ID
Результатом выполнения запроса будет следующая таблица:
| ID | Name |
| 10 | Sanders |
| 30 | Marenghi |
| 100 | Plotz |
| 140 | Fraye |
| 160 | Molinare |
| 240 | Daniels |
Теперь требуются данные, в которых объединены критерии отбора, применённые в двух запросах. Объединяем запросы при помощи оператора UNION:
SELECT ID, Name FROM STAFF WHERE SALARY > 21000 UNION SELECT ID, Name FROM STAFF WHERE Job = ‘Mgr’ AND Years ORDER BY ID
Результатом выполнения запроса с оператором UNION будет следующая таблица:
| ID | Name |
| 10 | Sanders |
| 30 | Marenghi |
| 100 | Plotz |
| 140 | Fraye |
| 160 | Molinare |
| 240 | Daniels |
| 260 | Jones |
Запрос с оператором UNION может возвращать и большее количество столбцов, важно, повторимся, чтобы в объединяемых запросах число столбцов, порядок их следования и типы данных совпадали.
Теперь работаем с базой данных «Портал объявлений — 1». Скрипт для создания этой базы данных, её таблицы и заполения таблицы данных — в файле по этой ссылке
Пример 5. Есть база данных портала объявлений.
Пусть сначала требуется получить данные о категориях и частях категорий объявлений, в которых подано более 100 объявлений в неделю. Пишем следующий запрос:
SELECT Category, Part, Units, Money FROM ADS WHERE Units > 100
Результатом выполнения запроса будет следующая таблица:
| Category | Part | Units | Money |
| Транспорт | Автомашины | 110 | 17600 |
| Транспорт | Мотоциклы | 131 | 20960 |
| Электротехника | Телевизоры | 127 | 8255 |
| Электротехника | Холодильники | 137 | 8905 |
| Стройматериалы | Регипс | 112 | 11760 |
| Досуг | Музыка | 117 | 7605 |
Теперь требуется извлечь данные о категориях и частях категорий объявлений, за которые выручено более 10000 денежных единиц в неделю. Пишем следующий запрос:
SELECT Category, Part, Units, Money FROM ADS WHERE Money > 10000
Результатом выполнения запроса будет следующая таблица:
| Category | Part | Units | Money |
| Транспорт | Автомашины | 110 | 17600 |
| Недвижимость | Квартиры | 89 | 18690 |
| Недвижимость | Дачи | 57 | 11970 |
| Транспорт | Мотоциклы | 131 | 20960 |
| Стройматериалы | Регипс | 112 | 11760 |
Теперь требуется извлечь данные, которые соответствуют критериям и первого, и второго запросов. Объединяем запросы при помощи оператора UNION:
SELECT Category, Part, Units, Money FROM ADS WHERE Units > 100 UNION SELECT Category, Part, Units, Money FROM ADS WHERE Money > 10000
Результатом выполнения запроса будет следующая таблица:
| Транспорт | Автомашины | 110 | 17600 |
| Транспорт | Мотоциклы | 131 | 20960 |
| Недвижимость | Квартиры | 89 | 18690 |
| Недвижимость | Дачи | 57 | 11970 |
| Электротехника | Телевизоры | 127 | 8255 |
| Электротехника | Холодильники | 137 | 8905 |
| Стройматериалы | Регипс | 112 | 11760 |
| Досуг | Музыка | 117 | 7605 |
Примеры запросов к базе данных «Портал объявлений-1» есть также в уроках об операторах INSERT, UPDATE, DELETE, HAVING.
- Итоги и индивидуальные значения в одной таблице с помощью оператора SQL UNION
- Другие случаи объединения запросов к одной таблице с помощью оператора SQL UNION
- Объединение результатов запросов к двум таблицам с помощью оператора SQL UNION
- Объединение результатов сложных запросов
Руководство по SQL. Объединения.
Для комбинирования результатов двух и более SQL запросов без возвращения повторяющихся данных используется оператор UNION.
Для того, чтобы мы могли использовать данный оператор, каждый из запросов SELECT должен содержать одинаковое количество выбранных колонок, одинаковое количество выражений, одинаковые типы данных и иметь одинаковый порядок.
Запрос с использованием оператора UNION имеет следующий вид:
SELECT колонка1 [, колонка2 ] FROM таблица1 [, таблица2 ] [WHERE условие] UNION SELECT колонка1 [, колонка2 ] FROM таблица1 [, таблица2 ] [WHERE условие]
Предположим, что у нас есть две таблицы:
developers:
+----+-------------------+------------+------------+--------+ | ID | NAME | SPECIALTY | EXPERIENCE | SALARY | +----+-------------------+------------+------------+--------+ | 1 | Eugene Suleimanov | Java | 2 | 2500 | | 2 | Peter Romanenko | Java | 3 | 3500 | | 3 | Andrei Komarov | JavaScript | 3 | 2500 | | 4 | Konstantin Geiko | C# | 2 | 2000 | | 5 | Asya Suleimanova | UI/UX | 2 | 1800 | | 6 | Kolya Nikolaev | Javascript | 5 | 3400 | | 7 | Ivan Ivanov | C# | 1 | 900 | | 8 | Ludmila Geiko | UI/UX | 2 | 1800 | +----+-------------------+------------+------------+--------+
tasks:
+---------+-------------+------------------+------------+--------------+ | TASK_ID | TASK_NAME | DESCRIPTION | DEADLINE | DEVELOPER_ID | +---------+-------------+------------------+------------+--------------+ | 1 | Bug#123 | Fix company list | 2016-06-03 | 1 | | 2 | Bug#321 | Fix registration | 2016-06-06 | 2 | | 3 | Feature#777 | Latest actions | 2016-06-25 | 3 | +---------+-------------+------------------+------------+--------------+
Попробуем выполнить следующий запрос:
mysql> SELECT ID, NAME, TASK_NAME, DEADLINE FROM developers LEFT JOIN tasks ON developers.ID = tasks.DEVELOPER_ID UNION SELECT ID, NAME, TASK_NAME, DEADLINE FROM developers RIGHT JOIN tasks ON developers.ID = tasks.DEVELOPER_ID;
В результате мы получим следующий результат:
+------+-------------------+-------------+------------+ | ID | NAME | TASK_NAME | DEADLINE | +------+-------------------+-------------+------------+ | 1 | Eugene Suleimanov | Bug#123 | 2016-06-03 | | 2 | Peter Romanenko | Bug#321 | 2016-06-06 | | 3 | Andrei Komarov | Feature#777 | 2016-06-25 | | 4 | Konstantin Geiko | NULL | NULL | | 5 | Asya Suleimanova | NULL | NULL | | 6 | Kolya Nikolaev | NULL | NULL | | 7 | Ivan Ivanov | NULL | NULL | | 8 | Ludmila Geiko | NULL | NULL | +------+-------------------+-------------+------------+
Элемент UNION ALL
Элемент UNION ALL комбинирует результаты двух запросов SELECT, исключая повторяющиеся записи.
Данный запрос имеет следующий вид:
SELECT колонка1 [, колонка2 ] FROM таблица1 [, таблица2 ] [WHERE условие] UNION ALL SELECT колонка1 [, колонка2 ] FROM таблица1 [, таблица2 ] [WHERE условие]
Предположим, что у нас есть две таблицы:
developers:
+----+-------------------+------------+------------+--------+ | ID | NAME | SPECIALTY | EXPERIENCE | SALARY | +----+-------------------+------------+------------+--------+ | 1 | Eugene Suleimanov | Java | 2 | 2500 | | 2 | Peter Romanenko | Java | 3 | 3500 | | 3 | Andrei Komarov | JavaScript | 3 | 2500 | | 4 | Konstantin Geiko | C# | 2 | 2000 | | 5 | Asya Suleimanova | UI/UX | 2 | 1800 | | 6 | Kolya Nikolaev | Javascript | 5 | 3400 | | 7 | Ivan Ivanov | C# | 1 | 900 | | 8 | Ludmila Geiko | UI/UX | 2 | 1800 | +----+-------------------+------------+------------+--------+
tasks:
+---------+-------------+------------------+------------+--------------+ | TASK_ID | TASK_NAME | DESCRIPTION | DEADLINE | DEVELOPER_ID | +---------+-------------+------------------+------------+--------------+ | 1 | Bug#123 | Fix company list | 2016-06-03 | 1 | | 2 | Bug#321 | Fix registration | 2016-06-06 | 2 | | 3 | Feature#777 | Latest actions | 2016-06-25 | 3 | +---------+-------------+------------------+------------+--------------+
Попробуем выполнить следующий запрос:
mysql> SELECT ID, NAME, TASK_NAME, DEADLINE FROM developers LEFT JOIN tasks ON developers.ID = tasks.DEVELOPER_ID UNION ALL SELECT ID, NAME, TASK_NAME, DEADLINE FROM developers RIGHT JOIN tasks ON developers.ID = tasks.DEVELOPER_ID;
В результате мы получим следующую таблицу:
+------+-------------------+-------------+------------+ | ID | NAME | TASK_NAME | DEADLINE | +------+-------------------+-------------+------------+ | 1 | Eugene Suleimanov | Bug#123 | 2016-06-03 | | 2 | Peter Romanenko | Bug#321 | 2016-06-06 | | 3 | Andrei Komarov | Feature#777 | 2016-06-25 | | 4 | Konstantin Geiko | NULL | NULL | | 5 | Asya Suleimanova | NULL | NULL | | 6 | Kolya Nikolaev | NULL | NULL | | 7 | Ivan Ivanov | NULL | NULL | | 8 | Ludmila Geiko | NULL | NULL | | 1 | Eugene Suleimanov | Bug#123 | 2016-06-03 | | 2 | Peter Romanenko | Bug#321 | 2016-06-06 | | 3 | Andrei Komarov | Feature#777 | 2016-06-25 | +------+-------------------+-------------+------------+
Как мы видим, таблица содержит результаты обоих запросов SELECT и данные повторяются.
Существует два других оператора, чьё поведение крайне схоже с UNION:
- INTERSECT
Комбинирует два запроса SELECT, но возвращает записи только первого SELECT, которые имеют совпадения во втором элементе SELECT. - EXCEPT
Комбинирует два запроса SELECT, но возвращает записи только первого SELECT, которые не имеют совпадения во втором элементе SELECT.
На этом мы заканчиваем изучение способов объединения данных.
В следующей статье мы рассмотрим индексы.
2.13. Объединение запросов
Допустим, что есть какая-то задача, которую вы не можете решить в один запрос. Например, допустим, что нужно выбрать из таблицы все записи, в которых в поле «vcName» указано имя Андрей, а в поле «vcSurName» указана фамилия Васильевич. При этом, если запись удовлетворяет и тому и другому условию, то она должна быть выведена в результате дважды. Как решить эту задачу? Если написать запрос:
SELECT vcFamil, vcName, vcSurName FROM tbPeoples WHERE vcName='Андрей' OR vcSurName='Васильевич'
То оба условия будут описаны верно, но в результате человек с именем и отчеством Андрей Васильевич попадет в результат только один раз, а нам надо два.
Проблема решается выполнением двух запросов. Сначала необходимо определить все записи с именем Андрей, а потом с отчеством Васильевич. Но это будет два набора результата. Как их объединить в один? Для этого между запросами нужно написать один из следующих операторов:
- UNION – объединить результат, и если есть строки, одинаковые для обоих результатов, то вывести только одну строку.
- UNION ALL – объединить результат и включить в него все строки, даже повторяющиеся в обоих наборах.
Для решения нашей задачи нужно использовать UNION ALL, чтобы ни одна строка не исчезла и если какая-то запись соответствует двум условиям, она должна попадать в результат дважды:
SELECT vcFamil, vcName, vcSurName FROM tbPeoples WHERE vcName='Андрей' UNION ALL SELECT vcFamil, vcName, vcSurName FROM tbPeoples WHERE vcSurName='Васильевич'
Как видите, это всего лишь два запроса, между которыми стоит ключевое слово UNION ALL. У объединения есть одно ограничение – сортировку надо указывать только во втором запросе. Если поставить оператор ORDER BY в первом запросе, то в результате вы получите ошибку. А если указать во втором, то сортироваться будет весь результат (обоих запросов) как одно целое.
Чтобы в результирующем наборе было видно, какая запись была получена первым запросом, а какая вторым, давайте добавим еще одну колонку к каждому из запросов, в которой будет отображаться текст с номером запроса:
SELECT vcFamil, vcName, vcSurName, 'Запрос 1' FROM tbPeoples WHERE vcName='Андрей' UNION ALL SELECT vcFamil, vcName, vcSurName, 'Запрос 2' FROM tbPeoples WHERE vcSurName='Васильевич'
Не все так красиво у оператора UNION. У него есть следующие ограничения в использовании:
- Количество и типы полей должны быть одинаковыми.
- Символьные поля должны иметь одинаковое число символов.
Подобные запросы очень эффективны, когда нужно обращаться к разным базам данных. Например, один запрос выбирает данные из базы данных Database1, а другой из Database2.
Если одного поля в одном из запросов нет, то его можно заменить. Например, допустим, что во втором запросе происходит обращение к таблице, в которой нет поля фамилии. Да, у нас обращение идет к одной и той же таблице, но мы просто представим такую ситуацию. Как можно решить проблему? Вместо поля можно указать какой-либо текст, например:
SELECT vcFamil, vcName, vcSurName, 'Запрос 1' FROM tbPeoples WHERE vcName='Андрей' UNION ALL SELECT 'Не найдено', vcName, vcSurName, 'Запрос 2' FROM tbPeoples WHERE vcSurName='Васильевич' ORDER BY vcFamil
В данном примере, во втором запросе вместо поля фамилии указывается текст ‘Не найдено’. Для числового поля, вместо не существующего поля, конечно же, нужно указать число.
Объединение, пересечение, вычитание запросов SQL
При запросах к базе данных часто необходимо делать объединение, пересечение и вычитание запросов.
1 янв. 2021 · 4 минуты на чтение
Следующий этап научиться объединять запросы, выполнять над ними операции пересечения и вычитания.
Спонсор поста
Оператор JOIN
JOIN — оператор языка SQL, который является реализацией операции соединения реляционной алгебры. Входит в раздел FROM операторов SELECT , UPDATE или DELETE .
Для выбора данных из нескольких таблиц необходимо перечислить имена требуемых таблиц в предложении FROM через запятую. В этом случае получим декартово произведение таблиц.
SELECT * FROM P, PD
База данных, используемая в примерах, находится в этом посте.
Существует два способа соединения таблиц:
1) Условие соединения указывается в предложении WHERE
Пример 1.
Пусть требуется вывести информацию о поставках в виде отношения R(pnum, pname, dnum, volume).
SELECT P.pnum, pname, dnum, volume FROM P, PD WHERE P.pnum=PD.pnum
2) Условие соединения указывается в предложении FROM
Синтаксис такого соединения следующий:
FROM INNER JOIN | LEFT [OUTER] JOIN | RIGHT [OUTER] JOIN ON .=
В соответствии с приведенным выше синтаксисом возможны следующие варианты соединения таблиц:
- Внутреннее соединение
- Внешнее соединение(левое, правое и полное)
Внутреннее соединение
С помощью внутреннего соединения выше рассмотренный пример можно записать следующим образом:
SELECT pname, dnum, volume FROM P INNER JOIN PD ON P.pnum=PD.pnum
Соединять можно и более двух таблиц.
Пример 2.
Пусть требуется вывести информацию о поставках в виде отношения R(pname, dname, volume) .
SELECT pname, dname, volume FROM (P INNER JOIN PD ON P.pnum=PD.pnum) INNER JOIN D ON PD.dnum=D.dnum
Пример 3.
Пусть требуется вывести информацию о поставках в виде отношения R(pname, dname, dprice, volume, cost) , где значения поля стоимость поставки cost определяются как dprice*volume .
| pname | dname | dprice | volume | cost |
|---|---|---|---|---|
| Иванов | Болт | 10 руб. | 100 | 1000 руб. |
SELECT pname, dname, str(dprice)+’руб.’ AS dprice, volume, str(dprice*volume)+’руб.’ AS cost FROM (P INNER JOIN PD ON P.pnum=PD.pnum) INNER JOIN D ON PD.dnum=D.dnum
При построении вычисляемых полей для строковых значений может быть использована операция конкатенации (соединения) строк, которая записывается с помощью символа & или + . Эта операция была использована для получения значений вычисляемых полей dprice и cost . Предварительно числовые значения были приведены к строке с помощью функции STR() .
Внешние соединение
Различают 3 вида внешних соединений:
- Левое внешнее соединение
- Правое внешнее соединение
- Полное внешнее соединение
Левое внешнее соединение
Левое внешнее соединение отношений А и В отличается от внутреннего тем, что в результирующее отношение добавляются все кортежи из отношения А (левой таблицы), при этом отсутствующие значения полей из отношения В (правой таблицы) будут заполняться NULL-значениями.
Полное внешние соединение
При выполнении полного внешнего соединения в результирующее отношение помещаются все кортежи из обоих отношений, неизвестные значения заполняются NULL-значениями.
Правое внешнее соединение
Правое соединение выполняется аналогично левому, но в результирующее отношение добавляются все кортежи из отношения B (правой таблицы).
Рандомный блок
Оператор UNION – Объединение
Для объединения запросов используется следующий синтаксис:
UNION [ALL]
По умолчанию оператор UNION удаляет повторяющиеся строки из результирующего набора. Если указан параметр ALL, то результат будет содержать все строки, в том числе повторяющиеся.
Объединяемые запросы должны быть совместимы между собой. В терминологии SQL это обозначает, что:
- Таблицы должны иметь одинаковое количество столбцов.
- Типы данных в соответствующих столбцах должны быть совместимыми.
Объединяемые запросы должны быть совместимы между собой. В терминологии SQL это обозначает, что:
- Таблицы должны иметь одинаковое количество столбцов.
- Типы данных в соответствующих столбцах должны быть совместимыми.
При объединении данных из столбцов с разными именами результирующему столбцу присваивается имя столбца из первого запроса.
К результату объединения рекомендуется применять предложение ORDER BY , где можно ссылаться только на имена столбцов левого запроса в операторе UNION .
Пример 4.
Пусть задана таблица P1.
| Номер | Наименование |
|---|---|
| 5 | Орлов |
Определим результат следующего объединения:
SELECT * FROM P1 UNION SELECT * FROM P WHERE pnum=1 ORDER BY Номер
| Номер | Наименование |
|---|---|
| 1 | Иванов |
| 5 | Орлов |
Пример 5.
Получить номера деталей, цена которых более 20 рублей или суммарное поставляемое количество более 500 штук.
Запрос разбивается на две части:
- Вывод номеров деталей, цена которых более 200 рублей.
- Вывод номеров деталей, которые поставляются в количестве более 500 штук.
Результирующая таблица получается при объединении двух частей запроса.
SELECT dnum FROM D WHERE dprice>20 UNION SELECT dnum FROM PD GROUP BY dnum HAVING sum(volume)>500 ORDER BY dnum
Пример 6.
Вывести информацию о деталях. В том случае если цена детали не указана вывести ‘цены нет’.
Запрос разбивается на две части:
- Вывод информации о деталях, для которых указана цена.
- Вывод информации о деталях, для которых не указана цена. В этом случае в предложении SELECT вместо атрибута dprice нужно указывать строковую константу ‘цены нет’.
SELECT dnum, dname, dprice FROM D WHERE dprice IS NOT NULL UNION SELECT dnum, dname, 'цены нет' FROM PD WHERE dprice IS NULL ORDER BY dnum
Оператор INTERSECT – Пересечение
Пересечение запросов выполняется с помощью оператора INTERSECT , который выполняется аналогично оператору UNION .
Пример 7.
Вывести номера деталей, которые поставляет и поставщик с номером 1, и поставщик с номером 2.
SELECT dnum FROM PD WHERE pnum=1 INTERSECT SELECT dnum FROM PD WHERE pnum=2
Оператор EXCEPT – Вычитание
Вычитание выполняется с помощью оператора EXCEPT , который выполняется аналогично оператору UNION .
Пример 8.
Вывести номера поставщиков, которые не поставляют детали в настоящее время.
SELECT pnum FROM P EXCEPT SELECT pnum FROM PD
Пример 9.
Вывести номера поставщиков, которые не поставляют деталь № 2.
SELECT pnum FROM P EXCEPT SELECT pnum FROM PD WHERE dnum=2
Пример 10.
Вывести номера поставщиков, которые поставляют только деталь № 1.
SELECT pnum FROM PD WHERE dnum=1 EXCEPT SELECT pnum FROM PD WHERE dnum<>1
Заключение
В заключение, операторы JOIN , UNION , INTERSECT и EXCEPT являются важными инструментами при работе с реляционными базами данных.
Оператор JOIN используется для соединения двух таблиц, а операторы UNION , INTERSECT и EXCEPT используются для объединения, пересечения и вычитания данных из двух или более таблиц.
В целом, знание этих операторов и умение применять их в соответствии с требованиями конкретной задачи может значительно упростить работу с базами данных и обеспечить более эффективный анализ данных.
