Отправляет email-рассылки с помощью сервиса Sendsay
  Все выпуски  

Новости сайта "Упражнения по SQL" (http://www.sql-ex.ru)


Информационный Канал Subscribe.Ru

Новости сайта "Упражнения по SQL (http://www.sql-ex.ru)" Выпуск 22 (12 февраля 2005 г.)

http://www.sql-ex.ru

Новым посетителям сайта

Сайт посвящен изучению языка, с помощью которого осуществляется взаимодействие с реляционными (и не только) СУБД. Суть обучения состоит в выполнении заданий на написание запросов к учебным базам данных; при этом система контролирует правильность выполнения заданий. В настоящее время реализованы все операторы подъязыка манипуляции данными (DML), которые включают в себя оператор извлечения данных SELECT, а также операторы модификации данных - INSERT, DELETE и UPDATE.

Мы надеемся, что справочного материала сайта окажется достаточно для самостоятельного обучения. Кроме того, свои решения вы можете обсудить на форуме сайта. Опытных же специалистов приглашаем проверить (продемонстрировать) свое мастерство и принять участие в соревновании, обеспечиваемом рейтинговой системой учета времени выполнения заданий. Фактически, рейтинг ведется на втором этапе тестирования, который начинается после решения 62-х задач первого этапа. При подсчете рейтинга каждого участника отбрасывается один самый худший показатель среди всех решенных им упражнений.

Имеется возможность получить сертификат по SQL DML при выполнении определенного количества заданий.


Новости сайта

§ Сбилась проверка задачи 19 DML, что было замечено Mjachin. Данные поправили.

Число участников рейтинга - 2670

Число участников второго этапа - 243

Лучшие результаты (ТОР 20)

No Person Number of
Sel_ex
Last_Sel Number of
DML_ex
Scores Days Days_2 LastSolved LastVisit
1 Зверев Д.Л. (dimzv) 76 136 19 198 450 2.291 27 Jan 2005 28 Jan 2005
2 Кувалкин К.С. (Cyrilus) 76 136 19 198 72 4.861 04 Feb 2005 11 Feb 2005
3 Сныткин В.Л. (Ded I) 76 136 19 198 142 7.398 22 Jan 2005 11 Feb 2005
4 Валуев Д.И. (Fiolent) 76 136 19 198 503 19.337 19 Jan 2005 12 Feb 2005
5 Hakobyan H.H. (hamlet) 76 136 19 198 114 33.952 21 Jan 2005 09 Feb 2005
6 Мельникова И.А. (Iris_m) 76 136 19 198 254 66.765 21 Jan 2005 11 Feb 2005
7 Шипунов И. (IAS) 76 136 19 198 243 82.012 11 Feb 2005 12 Feb 2005
8 Spirin (spirin) 75 136 19 195 158 13.467 21 Jan 2005 24 Jan 2005
9 Иткин И.Л. (joseph_itkin) 75 136 18 193 340 2.809 31 Jan 2005 08 Feb 2005
10 Леденев С.А. (Shurgenz) 73 136 19 193 146 8.298 11 Jan 2005 11 Jan 2005
11 Михайлов В.Г. (mslava) 73 136 17 189 498 9.731 26 Oct 2004 26 Oct 2004
12 Галиаскаров Э.Г. (edart) 64 124 19 175 80 39.658 10 Feb 2005 11 Feb 2005
13 Пятница О.А. (Robin) 65 128 17 174 606 70.821 22 Oct 2004 06 Feb 2005
14 Якутин Н.В. (ZrenBy) 73 136 6 169 511 3.991 14 Sep 2004 18 Jan 2005
15 Рассказов А. (ra) 61 121 19 168 70 29.764 28 Jan 2005 30 Jan 2005
16 Губарь Д.К. (DEathkNIghtS) 61 124 17 166 23 1.046 03 Nov 2004 03 Nov 2004
17 Смирнов А. (Leshich) 61 124 17 166 205 84.171 30 Sep 2004 19 Nov 2004
18 Gershovich (VIG) 58 121 17 159 629 6.899 30 Nov 2004 11 Feb 2005
19 Булаев В.В. (Kvix) 58 121 17 159 124 24.267 27 Dec 2004 06 Jan 2005
20 Забара М.С. (максим111) 58 121 17 159 122 67.157 30 Dec 2004 14 Jan 2005
21 Карабанов А. (gipa) 70 133 0 157 139 5.019 10 Jul 2004 10 Jul 2004
22 сафрошкин В.Ю. (safervas) 60 123 14 156 103 80.138 26 Nov 2004 12 Dec 2004

Лучшие результаты за неделю

No surname n_sel sel_all sel_scores dml_scores scores rating last_visit
1 >Гневашев Е.С. (esg) 55 55 96 17 113 304 12 Feb 2005
2 Чистяков А.Ю. (MEF444) 56 56 98 6 104 284 07 Feb 2005
3 Ерёмкин М.С. (Миша Е.) 52 52 88 9 97 346 10 Feb 2005
4 Бурсов В. (Moonspell) 45 58 88 1 89 276 11 Feb 2005
5 Чепрасов О.А. (Olegov) 27 42 57 18 75 427 11 Feb 2005
6 Куликов П. (kulpavel) 20 69 48 21 69 117 11 Feb 2005
7 Смагин С. (Dec) 28 28 49 11 60 642 07 Feb 2005
8 Середа С. (Diletant) 25 40 52 6 58 457 10 Feb 2005
9 Медников М.В. (medniy) 30 54 55 0 55 324 10 Feb 2005
10 Mikhailenko H. (Reset) 29 29 52 3 55 622 09 Feb 2005
11 Workman (Workman) 23 59 42 9 51 261 10 Feb 2005
12 Довжик А.А. (Kain) 23 55 42 9 51 305 10 Feb 2005
13 Кубин А.Л. (NoName) 28 56 49 0 49 289 09 Feb 2005
14 Самохвалова С.А. (Lu) 28 39 46 1 47 588 11 Feb 2005
15 Nikolaev S.V. (snikol) 9 60 21 23 44 257 10 Feb 2005
16 Хромченков Д.А. (olap) 16 60 38 5 43 255 11 Feb 2005
17 Мартюшина Д.А. (Pers) 32 32 40 3 43 778 11 Feb 2005
18 Конаков Д.А. (HellFire) 31 31 38 3 41 803 11 Feb 2005
19 >Овчинников Г.В. (german) 24 24 37 1 38 819 12 Feb 2005
20 Pinchusovich S. (PSasha) 24 24 37 0 37 830 11 Feb 2005
21 Мельман И. (iranka) 8 61 17 19 36 221 11 Feb 2005
22 Akudovich Y. (heropb) 17 42 34 0 34 432 11 Feb 2005
23 >Аверьянова Л. (Aversana) 25 25 33 0 33 942 12 Feb 2005
24 Veklenko D.S. (VDS) 22 22 32 0 32 950 11 Feb 2005

Изучаем SQL

Эти "хитрые" внешние соединения

Пусть требуется для каждого класса определить все корабли с известным годом спуска на воду. Когда говорится "для каждого класса", мы уже знаем, что нужно использовать внешнее соединение, например, левое:

SELECT Classes.class, name, launched FROM Classes
LEFT JOIN Ships ON Classes.class=Ships.class
   AND launched IS NOT NULL

Т.е. мы соединяем таблицу Classes с таблицей Ships по столбцу class и отбираем корабли с известным годом спуска на воду. Вот что, помимо прочего, мы имеем в результате:

class name launched
Bismarck NULL NULL

Как же так? Мы же указывали в предикате соединения launched IS NOT NULL? В словах "в предикате соединения" как раз и кроется ответ на наш вопрос. Вернемся к определению внешнего левого соединения:

Соединяются все строки из левой таблицы с теми строками из правой, для которых значение предиката истинно. Если для какой-либо строки из левой таблицы нет НИ ОДНОЙ соответствующей строки из правой таблицы, то значения столбцов правой таблицы получают значение NULL.

В таблице Ships нет ни одного корабля класса Bismarck. Потому мы и получили эту строку, т.к. класс Bismarck есть в таблице Classes. А если бы такой корабль был? Давайте добавим в таблицу Ships два корабля класса Bismarck - один с известным годом спуска на воду, а другой - с неизвестным:

SELECT * FROM Ships
UNION ALL
SELECT 'B_1' AS name, 'Bismarck' AS class, 1941 AS launched
UNION ALL
SELECT 'B_2' AS name, 'Bismarck' AS class, NULL AS launched

Перепишем наше решение с учетом этих новых кораблей:

SELECT Classes.class, name, launched FROM Classes
LEFT JOIN (
    SELECT * FROM Ships
    UNION ALL
    SELECT 'B_1' AS name, 'Bismarck' AS class, 1941 AS launched
    UNION ALL
    SELECT 'B_2' AS name, 'Bismarck' AS class, NULL AS launched
) Ships ON Classes.class = Ships.class
    AND launched IS NOT NULL

Теперь получаем ожидаемый результат, а именно, в результирующем наборе будет присутствовать только один корабль класса Bismarck:

class name launched
Bismarck B_1 1941

Вывод. Если вам нужно ограничить результирующий набор внешнего соединения, используйте предложение WHERE, которое и служит для этой цели:

SELECT Classes.class, name, launched FROM Classes
LEFT JOIN Ships ON Classes.class=Ships.class
    WHERE launched IS NOT NULL

Предикат же соединения определяет лишь то, какие строки из разных таблиц будут конкатенированы в результирующем наборе.

В заключении замечу, что данный пример не является вполне показательным, т.к. для решения поставленной задачи вполне подошло бы внутреннее соединение (INNER JOIN), несмотря на слова "для каждого класса". Однако гибкость языка SQL позволяет решить задачу разными способами, и использование стереотипов вполне оправдано.

§ Приведенные здесь примеры можно выполнить непосредственно на сайте, установив флажок "Без проверки" на странице с упражнениями на SELECT.

Контакты

По всем вопросам, связанным с функционированием сайта, проблемами при решении упражнений, идеями вы можете обращаться к Сергею И.Моисеенко msi77@yandex.ru. Вы также можете предложить свои задачи для публикации на сайте.

Подписка Subscribe.Ru
Новости сайта "Упражнения по SQL"

http://subscribe.ru/
http://subscribe.ru/feedback/
Подписан адрес:
Код этой рассылки: comp.soft.db.sqlex
Отписаться

В избранное