Добавил:
Upload Опубликованный материал нарушает ваши авторские права? Сообщите нам.
Вуз: Предмет: Файл:

SQL в вопросах и задачах

.pdf
Скачиваний:
34
Добавлен:
21.05.2015
Размер:
917.91 Кб
Скачать

61

ему з нач ение UNKNOWN. Поэтому рез ульта те в ып олнения п од з ап роса не буд ет п олуч ено ни од ного з нач енияи п од з ап рос п римет з нач ениело ж ь. Э то в св ою оч еред ьсд елает NOT EXISTS истинным, и, след ов ательно, строка с

NULL з нач ением п оле RATING п оп а д ет в ыход ные д а нные.

По смыслу

з ап роса такой рез ультат яв ляется неп рав ильным, так как на

са мом д еле

рейтинг унив ерситета, оп исыв аемого д анной строкой может бытьи больше

рейтинга какого-либо москов ского

унив ерситета (он п росто неиз в естен).

У каз анна яп роблема св яз а на с тем,

ч то з на ч ениеEXISTS в сегд а п р инимает

з нач енияи ст и на или ло ж ь, и никогд а – UNKNOWN. Э то яв ляетсяд ов од омд ля

исп ольз ов анияв таких случ аях оп ер атора ANY в место EXISTS.

2.14. И спол ь з ование COUNT вм ест о EXISTS

При отсутств ии NULL-з нач ений оп ера тор EXISTS может быть исп ольз ов ан в место ANY и ALL. Такжев место EXISTS и NOT EXISTS могут бытьисп ольз ов а ны тежесамыеп од з а п росы, но с исп ольз ов анием COUNT(*) в п ред ложении SELECT. Н а п ример, з ап рос

SELECT *

FROM UNIVERSITY A

WHERE NOT EXISTS

(SELECT *

FROM UNIVERSITY B

WHERE A.RATING > = B.RATING

AND B.CITY = ‘М о сква ’);

может бытьп ред став лен и след ующ емв ид е

SELECT *

FROM UNIVERSITY A

WHERE 1 >

(SELECT COUNT(*)

FROM UNIVERSITY B

WHERE A.RATING > = B.RATING

AND B.CITY = ‘М о сква ’);

 

 

62

 

 

УП Р АЖ НЕ НИ Я

 

 

 

 

37.Н а п ишите з а п рос,

в ыбира ющ ий

д анные о наз в аниях

унив ерситетов ,

р ейтинг которых

ра в ен или

п рев осход ит

рейтинг

Воронежского

госуд а рств енного унив ер ситета.

 

 

 

38.Н а п ишитез а п рос,

исп ольз ующ ий ANY или ALL,

в ып олняющ ий в ыборку

д анных о студ ента х, у которых в город еих п остоянного местожительств а нет унив ерситета .

39.Н а п ишите з ап рос, в ыбира ющ ий

из таблицы

EXAM_MARKS д а нные о

наз в а ниях п ред метов обуч ения,

д ля которых

з нач ение п олуч енных

на

э кз амене оценок (п оле MARK) п рев ышает любое з нач ение оценки

д ля

п ред мета , имеющ его ид ентифика тор рав ный 105.

 

40.Н а п ишитеэ тот жез ап рос с исп ольз ов аниемMAX.

2.15. О перат ор объ единения UNION

О п ера тор UNION исп ольз уетсяд ляобъед иненияв ыход ных д а нных д в ух или болееSQL-з ап росов в ед иноемножеств о строк и столбцов . Н а п ример,

д ля того,

ч тобы п олуч ить в од ной таблице фа милии и ид ентификаторы

студ ентов

и п реп од ав ателей из М оскв ы, можно исп ольз ов а тьслед ующ ий

з ап рос.

 

SELECT С туден т______’, SURNAME, STUDENT_ID

FROM STUDENT

WHERE CITY = ‘М о сква

UNION

SELECT Пр епо да ва тель’, SURNAME, LECTURER_ID

FROM LECTURER

WHERE CITY = ‘М о сква ’;

О братите в нима ние на

то, ч то

симв олом “;” (точ ка

с

з ап ятой)

оканч ив ается только п ослед ний з ап рос.

О тсутств иеэтого симв ола

в конце

SELECT-з ап роса оз на ч ает, ч то след ующ ий з а ним з ап рос также,

как и он

сам, яв ляетсяч а стьюобщ его з ап роса с UNION.

 

 

Исп ольз ов а ние оп ера тора

UNION в оз можно только п р и

объед инении

 

63

 

 

з ап росов ,

соотв етств ующ иестолбцы которых со в м ест и м ы по

о бъ ед и нени ю.

То есть,

соотв етств ующ ие ч ислов ые п оля

д олжны иметь п олностью

сов п а д ающ ие тип и р аз мер, симв ольные

п оля д олжны

иметь точ но

сов п а д ающ ее колич еств о симв олов . Е сли NULL-з нач ения з а п рещ ены д ля столбца хотя бы од ного любого п од з ап роса объед инения, то они д олжны бытьз ап рещ ены и д ляв сех соотв етств ующ их столбцов в д ругих п од з ап р осах объед инения.

2.16. Уст ранение дубл ирования в UNION

В отлич ие от обыч ных з а п росов UNION а в томатич ески исключ ает из в ыход ных д а нных д ублика ты строк, на п ример, в з ап р осе

SELECT CITY

FROM STUDENT

UNION

SELECT CITY

FROM LECTURER;

сов п а д ающ иена именов а ниягор од ов буд ут исключ ены.

Е сли в се же необход имо кажд ом з ап росе в ыв ести в се строки нез а в исимо от того, имеются ли такие же строки в д ругих объед иняемых з ап росах, то след ует исп ольз ов атьв о множеств енном з ап росеконструкциюс оп ераторомUNION ALL. Так в з ап росе

SELECT CITY

FROM STUDENT

UNION ALL

SELECT CITY

FROM LECTURER;

д ублика ты з на ч ений город ов , в ыв од имые в тор ой ч астью з ап роса, небуд ут исключ аться.

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

SELECT ма кс о ц’, A.STUDENT_ID, SURNAME, MARK, EXAM_DATE

64

FROM STUDENT A, EXAM_MARKS B WHERE (A.STUDENT_ID = B.STUDENT_ID

AND B.MARK =

(SELECT MAX(MARK)

FROM EXAM_MARKS C

WHERE C.EXAM_DATE = B.EXAM_DATE))

UNION ALL

SELECT ми н о ц ’, A.STUDENT_ID, SURNAME, MARK, EXAM_DATE FROM STUDENT A, EXAM_MARKS B

WHERE (A.STUDENT_ID = B.STUDENT_ID AND B.MARK =

(SELECT MIN(MARK)

FROM EXAM_MARKS C

WHERE C.EXAM_DATE = B.EXAM_DATE));

Д ляотлич иястрок, в ыв од имых п ерв ой и в торой ч астями з а п роса, в них

в ста в лены текстов ыеконста нты ‘ма кс о ц’и ‘ми н

о ц ’.

 

В п рив ед енном з а п росе агрегирующ ие

функции

исп ольз уются в

п од з ап росах. Э то

яв ляется нерациона льным

с точ ки

з рения в ремени,

з атр ач ив аемого на

в ып олнениез а п роса (см. раз д ел 2.9).

Б олееэффектив на

форма з ап роса, в оз в ращ ающ его а налогич ный рез ультат:

SELECT ма кс о ц’, A.STUDENT_ID, SURNAME, E.MARK, E.EXAM_DATE FROM STUDENT A,

(SELECT B.STUDENT_ID, B.MARK, B.EXAM_DATE FROM EXAM_MARKS B,

(SELECT MAX(MARK) AS MAX_MARK, C.EXAM_DATE FROM EXAM_MARKS C

GROUP BY C.EXAM_DATE) D

WHERE B.EXAM_DATE=D.EXAM_DATE AND B.MARK=MAX_MARK) E

WHERE A.STUDENT_ID=E.STUDENT_ID

UNION ALL

SELECT ми н о ц ’, A.STUDENT_ID, SURNAME, E.MARK, E.EXAM_DATE FROM STUDENT A,

(SELECT B.STUDENT_ID, B.MARK, B.EXAM_DATE FROM EXAM_MARKS B,

(SELECT MIN(MARK) AS MIN_MARK, C.EXAM_DATE FROM EXAM_MARKS C

GROUP BY C.EXAM_DATE) D

65

WHERE B.EXAM_DATE=D.EXAM_DATE

AND B.MARK=MIN_MARK) E

WHERE A.STUDENT_ID=E.STUDENT_ID

2.17. И спол ь з ование UNION сORDER BY

Пред ложение ORDER BY

п рименяется д ля уп оряд оч ения в ыход ных

д анных объед инения з а п росов

та к же,

как и д ля отд ельных з ап росов .

Послед ний п ример, п р и необход имости

уп оряд оч ения в ыход ных д анных

з ап роса п о фамилиямстуд ентов и д ата мэкз аменов , может в ыгляд етьтак:

SELECT ма кс о ц’, A.STUDENT_ID, SURNAME, E.MARK, E.EXAM_DATE FROM STUDENT A,

(SELECT B.STUDENT_ID, B.MARK, B.EXAM_DATE FROM EXAM_MARKS B,

(SELECT MAX(MARK) AS MAX_MARK, C.EXAM_DATE FROM EXAM_MARKS C

GROUP BY C.EXAM_DATE) D WHERE B.EXAM_DATE=D.EXAM_DATE AND B.MARK=MAX_MARK) E

WHERE A.STUDENT_ID=E.STUDENT_ID

UNION ALL

SELECT ми н о ц ’, A.STUDENT_ID, SURNAME, E.MARK, E.EXAM_DATE FROM STUDENT A,

(SELECT B.STUDENT_ID, B.MARK, B.EXAM_DATE FROM EXAM_MARKS B,

(SELECT MIN(MARK) AS MIN_MARK, C.EXAM_DATE FROM EXAM_MARKS C

GROUP BY C.EXAM_DATE) D

WHERE B.EXAM_DATE=D.EXAM_DATE AND B.MARK=MIN_MARK) E

WHERE A.STUDENT_ID=E.STUDENT_ID ORDER BY SURNAME, E.EXAM_DATE;

66

2.18. В неш нее объ единение

Ч асто п олез на оп ерация объед инения д в ух з ап росов , в которой в торой

з ап рос в ыбира ет строки,

исключ енныеп ер в ым. Та кая оп ерация наз ыв ается

в нешнимобъед инением.

 

 

 

 

 

 

 

Рассмотрим п ример.

Пусть в

таблице STUDENT имеются з ап иси о

студ ентах,

в которых

не указ ан

ид ентификатор унив ерситета.

Требуется

соста в итьсп исок студ ентов

с указ анием на именов а нияунив ерситета д лятех

студ ентов ,

у которых

эти

д анные есть,

но

п ри э том не отбра сыв ая и

студ ентов ,

у которых унив ерситет не ука з ан. М ожно

п олуч итьжелаемые

св ед ения,

сфор миров а в

 

объед инение д в ух

з а п росов ,

од ин из

которых

в ып олняет в ыборку

студ ентов с наз в а ниями

их унив ерситетов ,

а в торой

в ыбирает студ ентов

с NULL-з нач ениями

п олеUNIV_ID. В д а нном случ ае

оказ ыв ается п олез ной

в оз можность в став ки

в з ап рос

констант,

в на шем

случ а е текстов ой конста нты ‘н е и звестен ’,

ч тобы отметитьв сп иске тех

студ ентов , у которых отсутств ует информацияоб унив ерситете.

 

SELECT SURNAME, NAME, UNIV_NAME

FROM STUDENT, UNIVERSITY

WHERE STUDENT.UNIV_ID = UNIVERSITY.UNIV_ID

UNION

SELECT SURNAME, NAME, ‘н еи звестен

FROM STUDENT

WHERE UNIV_ID IS NULL

ORDER BY 1;

Д ля сов местимости столбцов объед иняемых з ап росов конста нту ‘н еи звестен ’ в о в торомз ап росеслед ует д оп олнитьп робела ми та к, ч тобы ее д лина соотв етств ов а ла д лине п оля UNIV_NAME или исп ольз ов ать д ля согла сов аниятип ов функцию CAST. В некоторых СУ Б Д согласов а ниетип ов п оляи з амещ ающ ей его текстов ой конста нты осущ еств ляетсяав томатич ески.

УП Р АЖ НЕ НИ Я

41.Соз д айте объед инение д в ух з ап росов , которые в ыд ают з нач ения п олей UNIV_NAME, CITY, RATING д ляв сех унив ерситетов . Теиз них, у которых р ейтинг рав ен или в ыше300, д олжны иметькомментарий ‘Вы со ки й’, в се остальные– ‘Н и зки й’.

67 42.Н а п ишите кома нд у, которая в ыд ает сп исок фа милий студ ентов , с

комментарием ‘успева ет’ у студ ентов ,

имеющ их в се п оложительные

оценки, комментарием ‘н е успева ет

д ля сд а в ав ших экз амены, но

имеющ их хотя бы од ну неуд ов летв орительную оценку, и комментарием ‘н е сда ва л’ – д ля в сех остальных. В в ыв од имом рез ультате фамилии студ ентов уп оряд оч итьп о а лфа в иту.

43.Выв ед итеобъед иненный сп исок студ ентов и п реп од ав ателей, жив ущ их в

М оскв е,

с

соотв етств ующ ими

комментариями

студен т’ или

пр епо да ва тель’.

 

 

44.Выв ед ите

объед иненный сп исок

студ ентов

и п реп од ав ателей

Воронежского

госуд арств енного унив ерситета с

соотв етств ующ ими

комментариями ‘студен т’ или ‘пр епо да ва тель’.

 

2.19.С оединение т абл иц сиспол ь зованием операт ора JOIN

Е сли в оп ератореSELECT п ослеключ ев ого слов а FROM указ ыв аетсяне од на, а д в е таблицы, то в рез ультате в ып олнения з ап р оса, в котором

отсутств ует

п ред ложение WHERE, кажд а я стр ока од ной таблицы буд ет

соед инена с

кажд ой стр окой в торой та блицы. Та кая оп ерация наз ыв ается

д ека р т о в ым

пр о и зв ед ени ем или по лны м (CROSS) со ед и нени ем таблиц баз ы

д анных. Сама п о себеэ та оп ерациянеимеет п рактич еского з нач ения, более того, п ри ошибоч ном исп ольз ов ании она может п рив ести к неожид анным

нештатным ситуа циям, так как в этом случ аев отв етена з ап рос колич еств о

з ап исей буд ет ра в но п роиз в ед ению ч исла з а п исей

соед иняемых таблица х,

то есть может оказ аться ч рез в ыч а йно большим.

Соед инениетаблиц имеет

смысл тогд а, когд а соед иняютсяне все строки

исход ных та блиц, а только те,

которые интересуют

п ольз ов ателя. Такое

огранич ение может быть

осущ еств лено с п омощ ью исп ольз ов а ния в

з ап росе

соотв етств ующ его

услов ия в п ред ложении

WHERE. Таким обр аз

ом, SQL п

оз в оляет в ыв од ить

информациюиз нескольких таблиц, св яз ыв аяих п о з нач ениямоп ред еленных п олей.

Н а п ример, если необход имо п олуч ить фамилии студ ентов

(та блица

STUDENT) и д ля кажд ого студ ента – наз в ания унив ерситетов

(та блица

68

UNIVERSITY), расп оложенных в город е, гд ежив ет студ ент, то необход имо п олуч ить в се комбина ции з ап исей о студ ентах и унив ерситетах в обеих таблица х, в которых з на ч ение п оля CITY сов п ад ает. Э то можно сд елатьс

помощ ьюслед ующ его з ап роса .

SELECT STUDENT.SURNAME, UNIVERSITY.UNIV_NAME, STUDENT.CITY FROM STUDENT, UNIVERSITY

WHERE STUDENT.CITY = UNIVERSITY.CITY;

Соед инение, исп ольз ующ ее п ред икаты,

основ а нные на

рав енств а х,

наз ыв а ется экви со ед и нени ем . Рассмотренный

п ример соед инения таблиц

относятся к в ид у так наз ыв аемого внут р еннего (INNER) со ед и нени я. При

таком тип есоед инения соед иняются только тестроки та блиц,

д ля которых

яв ляется истинным п р ед икат, з ад ав аемый в п ред ложении ON в ып олняемого з ап роса.

Прив ед енный в ышез ап рос может бытьз а п исан инач е, с исп ольз ов а нием ключ ев ого слов а JOIN.

SELECT STUDENT.SURNAME, UNIVERSITY.UNIV_NAME, STUDENT.CITY

FROM STUDENT INNER JOIN UNIVERSITY

ON STUDENT.CITY = UNIVERSITY.CITY;

К люч ев ое слов о INNER в з ап р осе может бытьоп ущ ено,

та к как эта

оп цияв оп ератореJOIN д ейств ует п о умолч анию.

 

 

 

Рассмотренный

в ыше

случ а й

п олного

соед инения

(д екартов а

п роиз в ед ения та блиц)

с исп ольз ов анием ключ ев ого слов а

JOIN

буд ет

в ыгляд етьслед ующ имобраз ом

 

 

 

 

SELECT * FROM STUDENT JOIN UNIVERSITY;

 

 

ч то экв ив а лентно

 

 

 

 

 

 

SELECT * FROM STUDENT, UNIVERSITY;

 

 

 

Заметим, ч то в

СУ Б Д

Oracle

з а д ав аемый

станд артом

яз ыка

SQL

оп ератор JOIN неп од д ержив ается.

69

2.19.1.О перац ии соединения т абл иц посредст вом ссы л очной ц ел ост ност и

Информация в таблица х STUDENT и

EXAM_MARKS уже св яз ана

п осред ств ом п оля STUDENT_ID. В таблице

STUDENT п оле STUDENT_ID

яв ляется п ер в ич ным ключ ом, а в таблице EXAM_MARKS,

ссыла ющ имся на

него в нешним ключ ом. Состояние св яз анных таким

обра з ом таблиц

наз ыв а етсясостоянием ссылоч ной целостности. В д анном случ а ессылоч ная

целостность этих таблиц

п од р аз умев ает, ч то

ка ж д о м у з нач ению п оля

STUDENT_ID в таблицеEXAM_MARKS о бяза т ельно соотв етств ует т а ко е ж е

зна чени е п оля STUDENT_ID в таблице STUDENT. Д ругими слов а ми, в

таблице EXAM_MARKS не может бытьз а п исей,

имеющ их ид ентификаторы

студ ентов , которых нет

та блице STUDENT.

Станд артное п рименение

оп ерации соед инениясостоит в из в леч ении д анных в терминах этой св яз и.

Ч тобы п олуч ить сп исок фамилий

студ ентов с п олуч енными ими

оценка ми и ид ентификатор ами п ред метов

можно исп ольз ов атьслед ующ ий

з ап рос:

 

SELECT SURNAME, MARK, SUBJ_ID

FROM STUDENT, EXAM_MARKS

WHERE STUDENT.STUDENT_ID = EXAM_MARKS.STUDENT_ID;

Тот же самый рез ультат может быть п олуч ен п ри исп ольз ов ании в з ап росе д ля з ад а ния оп ерации соед инения таблиц ключ ев ого слов а JOIN. Зап рос с оп ера торомJOIN в ыгляд ит след ующ имобраз ом

SELECT SURNAME, MARK

FROM STUDENT JOIN EXAM_MARKS

ON STUDENT.STUDENT_ID = EXAM_MARKS.STUDENT_ID;

Х отя в ышереч ьшла о соед инении д в ух таблиц, можно сформиров ать

з ап росы п утемсоед иненияболееч емд в ух таблиц.

 

Пусть требуется на йти фамилии в сех студ ентов ,

п олуч ив ших

неуд ов летв ор ительнуюоценку, в местес наз в а ниями п р ед метов

обуч ения, п о

которымп олуч ена э та оценка .

 

SELECT SUBJ_NAME, SURNAME, MARK

FROM STUDENT, SUBJECT, EXAM_MARKS

WHERE STUDENT.STUDENT_ID = EXAM_MARKS.STUDENT_ID AND SUBJECT.SUBJ_ID = EXAM_MARKS.SUBJ_ID

70

AND EXAM_MARKS.MARK = 2;

То жесамоес исп ольз ов а ниемоп ератор а JOIN

SELECT SUBJ_NAME, SURNAME, MARK

FROM STUDENT JOIN SUBJECT JOIN EXAM_MARKS ON STUDENT.STUDENT_ID = EXAM_MARKS.STUDENT_ID

AND SUBJECT.SUBJ_ID = EXAM_MARKS.SUBJ_ID AND EXAM_MARKS.MARK = 2;

2.19.2.

В неш нее соединение т абл иц

К ак

отмеч а лось ранее, п ри исп ольз ов а нии внут р еннего (INNER)

соед инениятаблиц соед иняютсятолько теих строки, в которых сов п ад ают

з нач ения п олей, з ад ав аемые в п р ед ложении WHERE з ап роса. О д нако в о

многих случ аях это может п рив ести к нежела тельной п отереинформа ции.

Рассмотрим ещ ераз

п рив ед енный в ышеп ример з а п роса на в ыборку сп иска

фамилий студ ентов

с п олуч енными ими оценка ми и

ид ентифика торами

п ред метов . Пр и исп ольз ов ании, ка к это было сд ела но в

р ассматрив аемом

п римере, в нутреннего соед иненияв рез ультат з а п роса неп оп ад ут студ енты, которыеещ енесд а в али экз амены и которые, след ов ательно, отсутств уют таблицеEXAM_MARKS. Е сли женеобход имо иметьз ап иси об этих студ ентах в в ыд ав аемом з ап росом сп иске, то можно п рисоед инить св ед ения о студ ентах, несд а в а в ших экз амен, п утем исп ольз ов а нияоп ератора UNION с соотв етств ующ имз ап росом. Н а п ример, след ующ имобра з ом:

SELECT SURNAME, CAST MARK AS CHAR(1), CAST SUBJ_ID AS CHAR(10) FROM STUDENT, EXAM_MARKS

WHERE STUDENT.STUDENT_ID = EXAM_MARKS.STUDENT_ID

UNION

SELECT SURNAME, CAST NULL AS CHAR(1), CAST NULL AS CHAR(10)

FROM STUDENT

WHERE NOT EXIST (SELECT *

FROM EXAM_MARKS

WHERE STUDENT.STUDENT_ID = EXAM_MARKS.STUDENT_ID);

(з д есьфункция п реобразов ания тип ов CAST исп ольз уется д ля обесп еч ения сов местимости тип ов п олей объед иняемых з а п росов ).

Соседние файлы в предмете [НЕСОРТИРОВАННОЕ]