Sunteți pe pagina 1din 5

Capitolul 7

Subinterogări

O subinterogare (subconsultare) constă în includerea unei interogări în altă


interogare. Subinterogările produc tabele temporare intermediare, fiind folosite ca
argumente ale frazelor SELECT de la nivelul superior.
 Operatorul IN
Exemplu: Fie baza de date FIRMA cu tabelele: DEPART (departamente), ANG
(angajaţi), SALGRD (grade salarizare). Să se afişeze ce salarii au colegii de departament ai
lui Toma:
SELECT nume, salariu, nrdepart as Departament FROM ang;
WHERE nrdepart IN (SELECT nrdepart FROM ang WHERE nume='Toma')

Limitări SQL în subinterogări: În Visual FoxPro se pot folosi maxim două niveluri
de interogare (fraza principală şi o interogare subordonată).
Exemplu: Care sunt subordonaţii lui Toma (angajaţii al căror manager este Toma)
şi în ce localitate lucrează:
O frază SELECT cu trei nivele de interogare (exemplu – figura 1), care generează
eroare în Visual FoxPro, poate fi înlocuită cu o frază SELECT principală care realizează
joncţiunea tabelelor DEPART şi ANG şi o interogare subordonată):

51
Soluţia este următoarea interogare pe 2 niveluri:
SELECT nume as Angajat,manager, loc as Localitate,;
d.nrdepart as Departament;
FROM depart d INNER JOIN ang a ON d.nrdepart=a.nrdepart;
WHERE manager IN
(SELECT codang FROM ang WHERE nume='Toma')
 Operatorii ALL, SOME, ANY permit utilizarea unui predicat de comparaţie
bazat pe unul dintre operatorii: =, <, >, <=, >=, <>, ce se aplică rezultatului unei
subinterogări. Semnificaţia operatorilor ALL, SOME, ANY este prezentată în tabelul 1:
Operator Semnificaţie
ALL Compară valoarea atributului/ expresiei cu toate valorile returnate de
subinterogare
ANY Compară valoarea atributului/ expresiei cu fiecare valoare returnată de
subinterogare
SOME Compară valoarea atributului/ expresiei cu fiecare valoare returnată de
subinterogare
Tabel 1

Exemplu (operatorul ALL): Să se afişeze angajaţii al căror salariu este cel mai mare
în departamentul unde lucrează:
SELECT DISTINCT nume as Angajat,functie,salariu,;
nrdepart as Departament FROM ang;
WHERE salariu >= ALL(SELECT salariu FROM ang;
GROUP BY nrdepart);
ORDER BY nrdepart
Exemplu (operatorul ANY): Să se afişeze angajaţii care nu sunt proiectanţi şi au
salariul cel mult cât al unui proiectant:
SELECT nume as Angajat,functie,salariu FROM ang;
WHERE salariu < ANY(SELECT salariu FROM ang;
WHERE functie='PROIECTANT')
Observaţii:
- Expresia ‚< ANY(SELECT …)’ înseamnă mai mic decât maximul valorilor returnate
de subinterogare
- Expresia ‚> ANY(SELECT …)’ înseamnă mai mare decât minimul valorilor returnate
de subinterogare.
Exemplu (operatorul SOME): Să se afişeze angajaţii care nu sunt proiectanţi şi au
salariul cel puţin cât al unui proiectant:
Metoda 1:
SELECT nume as Angajat,functie,salariu;
FROM ang;
WHERE salariu > SOME(SELECT salariu FROM ang;
WHERE functie='PROIECTANT')

52
Metoda 2:
SELECT nume as Angajat,functie,salariu;
FROM ang;
WHERE salariu > ANY(SELECT salariu FROM ang;
WHERE functie='PROIECTANT')
Observaţii:
- Expresia ‚< SOME(SELECT …)’ înseamnă mai mic decât maximul valorilor returnate
de subinterogare.
- Expresia ‚> SOME(SELECT …)’ înseamnă mai mare decât minimul valorilor returnate
de subinterogare.
Concluzie: Operatorii ANY şi SOME sunt sinonimi.
 Operatorul EXISTS permite legarea frazei SELECT principale de una sau mai
multe subinterogări. Prin EXISTS se defineşte un predicat care are valoarea logică
‚adevărat’ dacă subinterogarea are ca rezultat un tabel cu cel puţin o linie.
Exemplu: Ce salarii au colegii de departament ai lui Toma (rezultatul este prezentat
în figura 2 ):
SELECT nume, salariu, nrdepart as Departament;
FROM ang a;
WHERE EXISTS ( SELECT * FROM ang b;
WHERE a.nrdepart =b.nrdepart and b.nume='Toma')

Observaţii:
- O interogare corelată este cea care urmează după operatorul EXISTS. Interogările
corelate pot fi legate folosind operatorul EXISTS sau operatorul IN.
- Folosirea operatorului IN determină crearea unor tabele temporare ce necesită timp de
execuţie mai mare decât la folosirea operatorului EXISTS.
- Operatorul EXISTS poate înlocui cu succes operatorul IN; reciproca nu este valabilă.
Exemplu: Care sunt subordonaţii lui Toma (codul angajatului Toma este 7698 –
rezultatul interogării este prezentat în figura 3):
Metoda 1: folosind operatorul IN
SELECT nume as Angajat,manager;
FROM ang;
WHERE manager IN (SELECT codang FROM ang;
WHERE nume='Toma')

53
Metoda 2: folosind operatorul EXISTS
SELECT nume as Angajat,manager;
FROM ang a;
WHERE EXISTS (SELECT codang ;
FROM ang b ;
WHERE nume='Toma' and a.manager=b.codang)

Intersecţia a două relaţii realizată cu operatorul EXISTS


Fie tabelele R1 şi R2 cu următoarele scheme relaţionale: R1(A, B, C) şi R2(C, D, E)
reprezentate prin tabelele 2 şi 3. Să se realizeze intersecţia celor două relaţii :

R1 R2
A B C C D E
20 xyz 30 25 xyz 30
30 xxz 20 40 yyz 25
40 yyz 25 30 xxz 40
Tabel 2 Tabel 3
SELECT ' Intersectia lui R1 cu R2' , * FROM R1;
WHERE EXISTS ( SELECT * FROM R2;
WHERE R1.A=R2.C AND R1.B=R2.D AND R1.C=R2.E)
Rezultatele interogării ce realizează intersecţia relaţiilor R1 şi R2 folosind
operatorul EXISTS sunt prezentate în figura 4:

Exemplu: Care sunt departamentele unde lucrează proiectanţi şi manageri:


SELECT nrdepart FROM ang a;
WHERE a.functie= 'PROIECTANT' AND ;
EXISTS ( SELECT nrdepart;
FROM ang b WHERE b.functie='MANAGER' ;

54
and a.nrdepart=b.nrdepart)

55

S-ar putea să vă placă și