- •Добряк Павел Вадимович управление данными
- •Управление данными
- • Угту-упи, 2012
- •Введение
- •1. Основные определения
- •1.1. Элементы баз данных
- •1.2. Технологии управления данными
- •1.3. Модели данных
- •2. Реляционная модель
- •2.1. Основные понятия реляционной модели
- •2.2. Нормализация
- •2.3. Проблемы проектирования реляционных баз данных
- •Задачи для самостоятельного решения
- •3. Реляционные алгебра и исчисления
- •3.1. Реляционная алгебра
- •3.2. Реляционное исчисление на кортежах
- •3.3. Реляционное исчисление на доменах
- •4.1. Введение в sql
- •4.2. Пример реляционной базы данных
- •4.3. Запросы к одной таблице
- •4.4. Запросы к нескольким таблицам
- •4.5. Вложенные запросы
- •4.6. Вложенные подзапросы и кванторы
- •4.7. Объединение однотипных запросов
- •4.8. Рекурсивные запросы
- •Объединение однотипных запросов.
- •Запросы для самостоятельного программирования
- •5. Olap и хранилища данных
- •5.1. Архитектура хранилищ данных
- •5.2. Аналитические запросы
- •6. Триггеры, хранимые процедуры, события
- •7. Транзакции
- •7.1. Функции транзакций
- •7.2. Уровни изолированности
- •7.3. Сериализация транзакций
- •7.4. Синхронизационный захват
- •7.5. Метод временных меток
- •8. Обзор перспективных направлений баз данных
- •9. Объектные технологии в субд
- •9.1. Три манифеста баз данных
- •9.2. Объектная модель sql
- •9.3. Модель данных odmg и язык oql
- •10. Запросы к интернет-страницам
- •10.1. Теговая парадигма
- •10.2. Язык запросов xQuery
- •11. Пространственные базы данных
- •12. Лабораторные работы
- •13. Курсовая работа
- •13.1. Концептуальное проектирование
- •13.2. Семантическое проектирование
- •13.3. Физическое проектирование. Реляционная модель данных
- •13.4. Запросы
- •Объединение однотипных запросов.
- •13.5. Интеллектуализация базы данных.
- •13.6. Клиентская часть информационной системы
- •13.7. Дополнительные элементы базы данных
- •Вопросы к экзамену
- •1. Основные определения.
- •2. Реляционная модель
- •3. Реляционные алгебра и исчисления
- •10. Запросы к интернет-страницам
- •11. Пространственные базы данных
- •Литература
- •Список иллюстраций список таблиц
- •Список листингов
- •Алфавитный указатель
- •Список сокращений
4.2. Пример реляционной базы данных
Изучение оператора SQL будем на примере реляционной БД, схема которой представлена на Рис. 15, состоящей из четырех таблиц, содержание которых приведено в Табл. 10 - Табл. 13.
Рис. 15. Схема базы данных «Продажи»
Табл. 10. Таблица «Продавцы»
Продавцы |
|||||
N |
Имя |
Отдел |
Город |
Зарплата |
N_Начальника |
1 |
Иванов |
опт |
Москва |
40000 |
1 |
2 |
Петров |
розница |
Екатеринбург |
10000 |
1 |
3 |
Сидоров |
опт |
Екатеринбург |
20000 |
1 |
4 |
Шмидт |
розница |
Москва |
30000 |
2 |
5 |
Зайцев |
розница |
Москва |
30000 |
2 |
Табл. 11. Таблица «Покупатели»
Покупатели |
||
N |
Имя |
Город |
1 |
Павлов |
Екатеринбург |
2 |
Андреев |
Москва |
3 |
Сергеев |
Екатеринбург |
Табл. 12. Таблица «Товары»
Товары |
||
N |
Название |
Количество |
1 |
Шило |
10 |
2 |
Мыло |
20 |
3 |
Яблоко |
30 |
Табл. 13. Таблица «Сделки»
Сделки |
||||||
N |
N_Продавца |
N_Покупателя |
N_Товара |
Количество |
Стоимость |
Дата |
1 |
1 |
1 |
2 |
10 |
230 |
01.01.2009 |
2 |
1 |
2 |
2 |
20 |
440 |
01.01.2009 |
3 |
1 |
1 |
1 |
30 |
360 |
02.01.2009 |
4 |
2 |
2 |
2 |
40 |
840 |
01.01.2009 |
5 |
3 |
3 |
1 |
50 |
550 |
01.01.2009 |
4.3. Запросы к одной таблице
Вывести все данные из таблицы продавцы (запрос приведен на Лист. 2, результат - Табл. 14):
Лист. 2. Запрос с операторами Select и From
SELECT *
FROM Продавцы;
Табл. 14. Результат запроса с операторами Select и From.
01 Select From |
|||||
N |
Имя |
Отдел |
Город |
Зарплата |
N_Начальника |
1 |
Иванов |
опт |
Москва |
40000 |
1 |
2 |
Петров |
розница |
Екатеринбург |
10000 |
1 |
3 |
Сидоров |
опт |
Екатеринбург |
20000 |
1 |
4 |
Шмидт |
розница |
Москва |
30000 |
2 |
5 |
Зайцев |
розница |
Москва |
30000 |
2 |
Вывести все данные из таблицы продавцы, отсортировав записи по отделам (запрос приведен на Лист. 3, результат -Табл. 15):
Лист. 3. Запрос с оператором Order By
SELECT *
FROM Продавцы
ORDER BY Отдел;
Табл. 15. Результат запроса с оператором Order By
02 Order By |
|||||
N |
Имя |
Отдел |
Город |
Зарплата |
N_Начальника |
3 |
Сидоров |
опт |
Екатеринбург |
20000 |
1 |
1 |
Иванов |
опт |
Москва |
40000 |
1 |
5 |
Зайцев |
розница |
Москва |
30000 |
2 |
4 |
Шмидт |
розница |
Москва |
30000 |
2 |
2 |
Петров |
розница |
Екатеринбург |
10000 |
1 |
Вывести все данные из таблицы продавцы, отсортировав записи по отделам и городам (запрос приведен на Лист. 4, результат - Табл. 16.):
Лист. 4. Запрос №2 с оператором Order By
SELECT *
FROM Продавцы
ORDER BY Отдел, Город;
Табл. 16. Результат запроса №2 с оператором Order By
03 Order By 2 |
|||||
N |
Имя |
Отдел |
Город |
Зарплата |
N_Начальника |
3 |
Сидоров |
опт |
Екатеринбург |
20000 |
1 |
1 |
Иванов |
опт |
Москва |
40000 |
1 |
2 |
Петров |
розница |
Екатеринбург |
10000 |
1 |
5 |
Зайцев |
розница |
Москва |
30000 |
2 |
4 |
Шмидт |
розница |
Москва |
30000 |
2 |
Вывести все отделы (запрос приведен на Лист. 5, результат - Табл. 17):
Лист. 5. Запрос с выводом атрибута
SELECT Отдел
FROM Продавцы;
Табл. 17. Результат запроса с выводом атрибута
04 Поле |
Отдел |
опт |
розница |
опт |
розница |
розница |
Вывести все отделы, исключив повторяющиеся записи (запрос приведен на Лист. 6, результат - Табл. 18):
Лист. 6. Запрос с оператором Distinct
SELECT DISTINCT Отдел
FROM Продавцы;
Табл. 18. Результат запроса с оператором Distinct
05 Distinct |
Отдел |
опт |
розница |
Вывести число наименований товаров, которые когда-либо были проданы (запрос приведен на Лист. 7):
Лист. 7. Запрос с операторами Distinct и Count
SELECT count (DISTINCT N_Товара)
FROM Сделки;
Вывести среднее количество проданных товаров по всем сделкам (запрос приведен на Лист. 8, результат - Табл. 19):
Лист. 8. Запрос с оператором avg
SELECT avg(Количество) AS Среднее_количество
FROM Сделки;
Табл. 19. Результат запроса с оператором avg
07_1 avg |
Среднее_количество |
30 |
Вывести минимальное количество проданных товаров по всем сделкам (запрос приведен на Лист. 9, результат - Табл. 20):
Лист. 9. Запрос с оператором min
SELECT Min(Количество) AS Минимальное_количество
FROM Сделки;
Табл. 20. Результат запроса с оператором min
07_2 min |
Минимальное_количество |
10 |
Вывести максимальное количество проданных товаров по всем сделкам (запрос приведен на Лист. 10, результат - Табл. 21):
Лист. 10. Запрос с оператором max
SELECT max(Количество) AS Максимальное_количество
FROM Сделки;
Табл. 21. Результат запроса с оператором max
07_3 max |
Максимальное_количество |
50 |
Вывести суммарное количество проданных товаров по всем сделкам (запрос приведен на Лист. 11, результат - Табл. 22):
Лист. 11. Запрос с оператором sum
SELECT sum(Количество) AS Суммарное_количество
FROM Сделки;
Табл. 22. Результат запроса с оператором sum
07_4 sum |
Суммарное_количество |
150 |
Ошибка №1. Часто в заданиях встречаются слова «число» или «количество». Нужно догадаться по смыслу, речь идет о количестве строк в некоторой группе записей, или о названии колонки в какой-либо таблице. В данном случае используется агрегирующий оператор count. Если бы речь шла о названии колонки, то нужно было бы догадаться о какой таблице идет речь. Так, например, в нашей базе данных «Количество» есть в таблице «Товары» (имеется в виду количество на складе) и в таблице «Сделки» (количество товара, проданного в сделке). Сравнение запросов см. в Табл. 23.
Табл. 23. Сравнение запросов на количество
Задание |
Запрос |
Вывести количество проданного товара |
select sum(Количество) from Сделки; |
Вывести количество наименований проданного товара |
select count(distinct N_Товара) from Сделки; |
Вывести количество товара (на складе) |
select sum(Количество) from Товары; |
Вывести количество наименований товара на складе |
select count(*) from Товары; |
Вывести цену единицы товара (запрос приведен на Лист. 12, результат - Табл. 24):
Лист. 12. Запрос с операциями над атрибутами
SELECT N, N_Продавца, N_Покупателя, N_Товара, Стоимость/Количество AS Цена
FROM Сделки
ORDER BY Сделки.N_Товара;
Табл. 24. Результат запроса с операциями над атрибутами
08 деление |
|||||
N |
N_Продавца |
N_Покупателя |
N_Товара |
Количество |
Цена |
3 |
1 |
1 |
1 |
30 |
12 |
5 |
3 |
3 |
1 |
50 |
11 |
1 |
1 |
1 |
2 |
10 |
23 |
2 |
1 |
2 |
2 |
20 |
22 |
4 |
2 |
2 |
2 |
40 |
21 |
Вывести информацию о сделках, стоимость которых больше 400 (запрос приведен на Лист. 13, результат - Табл. 25):
Лист. 13. Запрос с оператором Where
SELECT N, N_Продавца, N_Покупателя, N_Товара, Количество, Стоимость
FROM Сделки
WHERE Стоимость>400;
Табл. 25. Результат запроса с оператором Where
09 Where |
|||||
N |
N_Продавца |
N_Покупателя |
N_Товара |
Количество |
Стоимость |
2 |
1 |
2 |
2 |
20 |
440 |
4 |
2 |
2 |
2 |
40 |
840 |
5 |
3 |
3 |
1 |
50 |
550 |
Вывести информацию о сделках, стоимость которых больше 400 и количеством проданного товара в сделке больше 30 (запрос приведен на Лист. 14, результат - Табл. 26):
Лист. 14. Запрос с операторами Where и And
SELECT N, N_Продавца, N_Покупателя, N_Товара, Количество, Стоимость
FROM Сделки
WHERE Стоимость>400
AND Количество>30;
Табл. 26. Результат запроса с операторами Where и And
10 Where And |
|||||
N |
N_Продавца |
N_Покупателя |
N_Товара |
Количество |
Стоимость |
4 |
2 |
2 |
2 |
40 |
840 |
5 |
3 |
3 |
1 |
50 |
550 |
Вывести номера продавцов и число сделок, ими заключенных (запрос приведен на Лист. 15, результат - Табл. 27):
Лист. 15. Запрос с операторами Group By и Count
SELECT N_продавца, count(*) as Количество_сделок
FROM Сделки
GROUP BY N_продавца;
Табл. 27. Результат запроса с операторами Group By и Count
11 Group By Count |
|
N_продавца |
Количество_сделок |
1 |
3 |
2 |
1 |
3 |
1 |
Вывести номера продавцов и максимальную стоимость их сделок (запрос приведен на Лист. 16, результат - Табл. 28):
Лист. 16. Запрос с оператором Group By и агрегирующей функцией
SELECT N_Продавца, min(Стоимость) As Минимальная_стоимость, avg(Стоимость) As Средняя_стоимость, max(Стоимость) As Максимальная_стоимость
FROM Сделки
GROUP BY N_Продавца;
Табл. 28. Результат запроса с оператором Group By и агрегирующей функцией
12 Group By агрегирующие функции |
|||
N_Продавца |
Минимальная_стоимость |
Средняя_стоимость |
Максимальная_стоимость |
1 |
230 |
343,333333333333 |
440 |
2 |
840 |
840 |
840 |
3 |
550 |
550 |
550 |
Ошибка №2. Не нужно путать операторы Group By и Order By. Order By только сортирует записи, а Group By объединяет их в группы. Причем для каждой группы на экран выводится только одна строка – результат обработки всех строк в группе.
Ошибка №3. При группировке поля, участвующие в группировке, перечисляются в select без агрегирующей операции, все остальные поля – с агрегирующей операцией.
Вывести номера продавцов, даты и максимальную стоимость их сделок на каждый день (запрос приведен на Лист. 17, результат - Табл. 29):
Лист. 17. Запрос №2 с оператором Group By
SELECT N_Продавца, Дата, max(Стоимость)
FROM Сделки
GROUP BY N_Продавца, Дата;
Табл. 29. Результат запроса №2 с оператором Group By
13 Group By 2 |
||
N_Продавца |
Дата |
Максимальная_стоимость |
1 |
01.01.2009 |
440 |
1 |
02.01.2009 |
360 |
2 |
01.01.2009 |
840 |
3 |
01.01.2009 |
550 |
Вывести номера продавцов и максимальную стоимость их сделок в случае, если средняя стоимость их сделок больше 500 (запрос приведен на Лист. 18, результат - Табл. 30):
Лист. 18. Запрос с оператором Having и агрегирующей функцией
SELECT N_Продавца, max(Стоимость) as Максимальная_стоимость
FROM Сделки
GROUP BY N_Продавца
HAVING avg(Стоимость)>500;
Табл. 30. Результат запроса с оператором Having и агрегирующей функцией
14 Having агрегирующая функция |
|
N_Продавца |
Максимальная_стоимость |
2 |
840 |
3 |
550 |
Ошибка №4. Не нужно путать применение where и having. Having используется при группировке, когда условие накладывается на поле с агрегирующей функцией. В данном примере - средняя стоимость их сделок больше 500. Если бы слово «средняя» отсутствовало, это было бы признаком использования where
Вывести номера продавцов и максимальную стоимость их сделок в случае, если средняя стоимость их сделок больше 500, отсортировать по максимальной стоимости (запрос приведен на Лист. 19, результат - Табл. 31):
Лист. 19. Запрос с операторами Having и Order By
SELECT N_Продавца, max(Стоимость) as Максимальная_стоимость
FROM Сделки
GROUP BY N_Продавца
HAVING avg(Стоимость)>500
ORDER BY avg(Стоимость);
Табл. 31. Результат запроса с операторами Having и Order By
15 Having Order By |
|
N_Продавца |
Максимальная_стоимость |
3 |
550 |
2 |
840 |
Вывести номера продавцов и максимальную стоимость их сделок в случае, если средняя стоимость их сделок больше 500 и максимальная стоимость сделок < 800 (запрос приведен на Лист. 20, результат - Табл. 32):
Лист. 20. Запрос с операторами Having и And
SELECT N_Продавца, max(Стоимость) as Максимальная_стоимость
FROM Сделки
GROUP BY N_Продавца
HAVING (avg(Стоимость)>500 And max(Стоимость)<800);
Табл. 32. Результат запроса с операторами Having и And
16 Having And |
|
N_Продавца |
Максимальная_стоимость |
3 |
550 |
Вывести номера продавцов и минимальную стоимость их сделок в случае, если номер продавца > 1 (запрос приведен на Лист. 21, результат - Табл. 33):
Лист. 21. Запрос с оператором Having без агрегирующей функции
SELECT N_Продавца, min(Стоимость) As Минимальная_стоимость
FROM Сделки
GROUP BY N_Продавца
HAVING N_Продавца>1;
Табл. 33. Результат запроса с оператором Having без агрегирующей функции
17 Having без агрегирующей |
|
N_Продавца |
Минимальная_стоимость |
2 |
840 |
3 |
550 |
Ошибка №5. Аналогично полям Select при группировке, те поля, которые перечисляются в Group By, могут использоваться в Having без агрегирующей операции; те, которых нет в Group By, используются в Having c агрегирующей операцией.
Вывести номера продавцов и максимальную стоимость тех сделок, кол-во товара которых больше 15, в случае, если максимальная стоимость этих сделок меньше 800 (запрос приведен на Лист. 22, результат - Табл. 34):
Лист. 22. Запрос с операторами Where, Group by и Having
SELECT N_Продавца, max(Стоимость) as Максимальная_стоимость
FROM Сделки
WHERE Количество>15
GROUP BY N_Продавца
HAVING max(Стоимость)<800;
Табл. 34. Результат запроса с операторами Where, Group by и Having
18 Where Group By Having |
|
N_Продавца |
Средняя_стоимость |
1 |
400 |
3 |
550 |
Ошибка №6. Не нужно путать порядок следования операторов: where, group by, having, order by
Ошибка №7. При совместном использовании операторов where, group by, having в одном запросе сперва осуществляется селекция по условию в where, затем происходит группировка и вычисление агрегирующих функций. Таким образом, при подсчете средних значений не учитываются записи, которые были отброшены. Так, в нашем примере, средняя стоимость по продавцу №1 меньше 400. Поэтому нужно смотреть по заданию, считать ли агрегирующие функции по отфильтрованным строкам или надо строить более сложный запрос.
Запрос, в задании которого приведены всевозможные стоимости, так что легко сделать несколько вышеперечисленных ошибок: Вывести номера продавцов с суммарной стоимостью тех сделок, в которых стоимость была больше 400, если эта суммарная стоимость больше 500, отсортировать по суммарной стоимости, приведен на Лист. 23, его результат – в Табл. 35. Обратите внимание, что продавец №1 отсеялся, несмотря на то, что суммарная стоимость его сделок больше 500. Почти все его сделки были со стоимостью меньше 400. Запрос сперва выполняет селекцию в where, а суммарный итог подводит по оставшимся записям.
Лист. 23. Запрос с операторами Where, Group by и Having, Order by
SELECT N_Продавца, sum(Стоимость) AS Суммарная_стоимость
FROM Сделки
WHERE Стоимость>400
GROUP BY N_Продавца
HAVING sum(Стоимость)>500
ORDER BY sum(Стоимость);
Табл. 35. Результат запроса с операторами Where, Group by и Having, Order by
18A Where Group By Having Order By |
|
N_Продавца |
Суммарная_стоимость |
3 |
550 |
2 |
840 |
