De presentatie wordt gedownload. Even geduld aub

De presentatie wordt gedownload. Even geduld aub

Hoofdstuk 8: Werken met SQL voor eindgebruikers. Overzicht Inleiding op SQL: de select-instructie Eenvoudige queries Join queries Nested queries Queries.

Verwante presentaties


Presentatie over: "Hoofdstuk 8: Werken met SQL voor eindgebruikers. Overzicht Inleiding op SQL: de select-instructie Eenvoudige queries Join queries Nested queries Queries."— Transcript van de presentatie:

1 Hoofdstuk 8: Werken met SQL voor eindgebruikers

2 Overzicht Inleiding op SQL: de select-instructie Eenvoudige queries Join queries Nested queries Queries met setoperatoren

3 Structured Query Language (SQL) Een datataal –voor het definiëren van een relationele database (DDL) –voor het behandelen van gegevens in een relationele database (DML) raadplegen van gegevens wijzigen van gegevens toevoegen van gegevens verwijderen van gegevens Set-georïenteeerde taal –SQL-opdrachten worden uitgevoerd op tabellen die geacht worden voorstellingen te zijn van genormaliseerde wiskundige relaties –Het resultaat van een SQL instructie kan opnieuw een tabel zijn –Geen procedureel programmeren. Theoretische onderbouwd –Relationele algebra (select, project, unie, doorsnede, verschil, product, deling, join) –Relationele calculus (  - er bestaat een element,  - voor alle elementen) Interactief of embedded

4 Voorbeeld: Aankoopadministratie LEVERANCIER (LEVNR, LEVNAAM, LEVADRES, LEVPLAATS, LEVSTATUS) PRODUCT (PRODNR, PRODNAAM, PRODKLEUR, HOEV_IN_VOORR) AANKOOPVOORWAARDEN (LEVNR, PRODNR, AANKOOPPRIJS, LEVERTERMIJN) AANKOOPORDER (AONR, AODATUM, LEVNR) AANKOOPORDERREGEL (AONR, PRODNR, BESTELHOEV)

5 CREATE TABLE LEVERANCIER (LEVNR CHAR(4) NOT NULL PRIMARY KEY, LEVNAAM VARCHAR(40) NOT NULL, LEVADRES VARCHAR(50), LEVPLAATS VARCHAR(20), LEVSTATUS SMALLINT); CREATE TABLE PRODUCT (PRODNR CHAR(6) NOT NULL PRIMARY KEY, PRODNAAM VARCHAR(40) NOT NULL, CONSTRAINT UC1 UNIQUE(PRODNAAM), PRODKLEUR VARCHAR(15), CONSTRAINT CC1 CHECK(PRODKLEUR IN (‘wit’, ‘groen’, ‘rood’, ‘grijs’, ‘oker’, ‘zwart’)), PRODGEWICHT DECIMAL (6,2), HOEV-IN-VOORR INTEGER); Voorbeeld: tabeldefinities

6 CREATE TABLE AANKOOPVOORWAARDEN (LEVNR CHAR(4) NOT NULL, AANKOOPPRIJS DECIMAL(8,2) COMMENT ON COLUMN AANKOOPPRIJS IS ‘AANKOOPPRIJS IN EUR’, LEVERTERMIJN TIME COMMENT ON COLUMN LEVERTERMIJN IS ‘LEVERTERMIJN IN DAGEN’, PRIMARY KEY (LEVNR, PRODNR), FOREIGN KEY (LEVNR) REFERENCES LEVERANCIER (LEVNR) ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (PRODNR) REFERENCES PRODUCT (PRODNR) ON DELETE CASCADE ON UPDATE CASCADE); Voorbeeld: tabeldefinities (vervolg)

7 CREATE TABLE AANKOOPORDER (AONR CHAR(4) NOT NULL PRIMARY KEY, AODATUM DATE, LEVNR CHAR(4) NOT NULL, FOREIGN KEY (LEVNR) REFERENCES LEVERANCIER (LEVNR) ON DELETE CASCADE ON UPDATE CASCADE); CREATE TABLE AANKOOPORDERREGEL (AONR CHAR(4) NOT NULL, PRODNR CHAR(6) NOT NULL, BESTELHOEV INTEGER, PRIMARY KEY (AONR, PRODNR) FOREIGN KEY (AONR) REFERENCES AANKOOPORDER (AONR) ON DELETE CASCADE ON UPDATE CASCADE, FOREIGN KEY (PRODNR) REFERENCES PRODUCT (PRODNR) ON DELETE CASCADE ON UPDATE CASCADE); Voorbeeld: tabeldefinities (vervolg)

8 SQL select-instructie SELECT-component FROM-component [WHERE-component] [GROUP BY-component] [HAVING-component] [ORDER BY-component]

9 Eenvoudige queries Onder eenvoudige queries verstaan wij vragen waarmee gegevens worden geraadpleegd die in één tabel aanwezig zijn. –In de FROM component van de select-instructie is dus maar één tabelnaam vermeld. Met de SELECT component worden kolommen geëxtraheerd. –Als expressies worden in de SELECT-component meestal namen gebruikt van kolommen die wij willen zien.

10 –SELECT LEVNR, LEVNAAM, LEVADRES, LEVPLAATS, LEVSTATUS FROM LEVERANCIER of –SELECT * FROM LEVERANCIER –SELECT LEVNR, LEVNAAM FROM LEVERANCIER –SELECT DISTINCT LEVNR FROM AANKOOPORDER –SELECT LEVNR, PRODNR, LEVERTERMIJN/30 AS MAAND-LEVERTERMIJN FROM AANKOOPVOORWAARDEN Eenvoudige queries zonder WHERE component

11 Wanneer in een select instructie ook een WHERE component aanwezig is, kan men met condities aangeven welke tabelrijen moeten worden geselecteerd. –In de WHERE component worden dus condities of predicaten opgelegd waaraan de op te halen rijen moeten voldoen. (equivalent met “select” operator van relationele algebra) –Voor het specificeren van condities waaraan rijen moeten voldoen, kunnen er in de WHERE component meerdere operatoren worden gebruikt: vergelijkingsoperatoren (, =,...) booleaanse operatoren (AND, OR, NOT) BETWEEN operator (x BETWEEN y AND z) -> x ≥ y and x ≤ z IN operator (IN (u,v,w)) -> x=u or x=v or x=w LIKE operator NULL operator Eenvoudige queries met WHERE component

12 –SELECT LEVNR, LEVNAAM FROM LEVERANCIER WHERE LEVPLAATS = ‘ANTWERPEN’; –SELECT LEVNR, LEVNAAM FROM LEVERANCIER WHERE LEVPLAATS = ‘ANTWERPEN’ AND LEVSTATUS > 75; –SELECT LEVNR, LEVNAAM FROM LEVERANCIER WHERE LEVSTATUS BETWEEN 75 AND 85; –SELECT PRODNR, PRODNAAM FROM PRODUCT WHERE PRODKLEUR IN (‘WIT’,’GROEN’); –SELECT PRODNR, PRODNAAM FROM PRODUCT WHERE PRODNAAM LIKE ‘AP%’; –SELECT LEVNR, LEVNAAM FROM LEVERANCIER WHERE LEVSTATUS IS NULL Eenvoudige queries met WHERE component (voorbeelden)

13 In de SELECT component kunnen er allerlei expressies voorkomen. Deze expressies mogen ook setfuncties zijn. Met setfuncties kunnen bewerkingen worden uitgevoerd op kolomwaarden van rijen die zich voor een bepaalde vraag kwalificeren. De belangrijkste setfuncties: –COUNT –MIN, MAX –SUM, AVG –STDEV, VARIANCE Eenvoudige queries met setfunctie in de SELECT component

14 –SELECT COUNT(*) FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’; –SELECT COUNT(AANKOOPPRIJS) FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’; –SELECT COUNT (DISTINCT AANKOOPPRIJS) FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’; –SELECT SUM(BESTELHOEV) AS TOTSOMBESTELLINGEN FROM AANKOOPORDERREGEL; –SELECT PRODNR, SUM(BESTELHOEV) AS SOMBESTELLINGEN FROM AANKOOPORDERREGEL WHERE PRODNR = ‘0117’; Eenvoudige queries met setfunctie (voorbeelden)

15 Aankoopvoorwaarden levnrprodnraankoopprijslevertermijn , , , , ,00-

16 –SELECT PRODNR, AVG(AANKOOPPRIJS) AS GEWOGEN-GEMIDDELDE-PRIJS FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’; –SELECT PRODNR, AVG(DISTINCT AANKOOPPRIJS) AS ONGEWOGEN-GEMIDDELDE-PRIJS FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’; –SELECT PRODNR, VARIANCE(AANKOOPPRIJS) AS PRIJSVARIANTIE FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’; –SELECT PRODNR, MIN(AANKOOPPRIJS) AS LAAGSTE PRIJS, MAX(AANKOOPPRIJS) AS HOOGSTE-PRIJS FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’; Eenvoudige queries met setfunctie (voorbeelden)

17 Met een GROUP BY component kunnen rijen worden gegroepeerd op basis van onderlinge overeenkomsten. –bv. rijen moeten eenzelfde waarde hebben voor een gespecificeerde kolom Met de HAVING component worden groepen van rijen geselecteerd die aan bepaalde condities voldoen. –de HAVING component kan enkel voorkomen als ook de GROUP BY component is gebruikt. –terwijl expressies in de WHERE component geen setfunctie kunnen hebben, kan dat in de HAVING component wel. Eenvoudige queries met GROUP BY en HAVING

18 Gevraagd: geef de nummers van de producten waarvoor tenminste twee bestellingen uitstaan. –SELECT PRODNR FROM AANKOOPORDERREGEL GROUP BY PRODNR HAVING COUNT(*) >1; Gevraagd: geef de nummers van de producten waarvoor meer dan 100 stuks in bestelling zijn. –SELECT PRODNR FROM AANKOOPORDERREGEL GROUP BY PRODNR HAVING SUM(BESTELHOEV) > 100; Eenvoudige queries met GROUP BY en HAVING (voorbeelden)

19 Indien men de rijen – die ontstaan als resultaat van het uitvoeren van een query – in een bepaalde logische volgorde wil tonen, moet een ORDER BY component aanwezig zijn. Er mag op elke kolom, die in de SELECT component is gespecificeerd, worden gesorteerd en er mag op meer dan één kolom worden gesorteerd. –default is ‘ascending’. Interpretatie van null-waarden. Eenvoudige queries met ORDER BY component

20 Gevraagd: sorteer alle uitstaande aankooporders volgens oplopende datum, en per dag volgens dalend leveranciernummer. –SELECT AONR, AODATUM, LEVNR FROM AANKOOPORDER ORDER BY AODATUM ASC, LEVNR DESC; Gevraagd: geef voor een bepaald product, de prijzen die leveranciers aanrekenen, in dalende volgorde. –SELECT PRODNR, LEVNR, AANKOOPPRIJS FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’ ORDER BY 3 DESC; Eenvoudige queries met ORDER BY (voorbeelden)

21 Join queries Met join queries kunnen gegevens worden samengevoegd of gefuseerd. Meestal gaat het om gegevens uit verschillende tabellen. –in de FROM component van de select instructie worden de namen gespecificeerd van de tabellen waarvan wij rijen willen samenvoegen Wij moeten dan voorwaarden opleggen waaronder rijen van tabellen mogen worden samengevoegd. –in de WHERE component worden dan de condities gespecificeerd waaromheen de join moet worden voltrokken –equi-join Voorts kunnen wij aangeven in welke kolommen uit de respectievelijke tabellen wij zijn geïnteresseerd.

22 Kolommen (vervolg) –wanneer een kolomnaam wordt gebruikt, die in meer dan één van de tabellen van de FROM component voorkomt, is het verplicht een tabelspecificatie voor de kolomnaam te vermelden. –het is evenwel de gewoonte om kolomnamen te kwalificeren met de naam van de tabel waarin de kolom voorkomt, wanneer gegevens gevraagd worden uit meerdere tabellen. Extra condities in de WHERE component kunnen zorgen voor het fijner filteren van de rijen die voor fusie in aanmerking komen. een SQL join query zonder WHERE component waarbij alle kolommen in het resultaat mogen verschijnen is in feite een algebraïsch product (SELECT * FROM a, b) Join queries (vervolg)

23 Gevraagd: geef nummer, naam en status van leveranciers die producten kunnen leveren, tezamen met de nummers van de producten die zij kunnen leveren en de aankoopprijs die ze hiervoor aanrekenen. Leverancier (levnr, levnaam,..., levstatus) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs,...) –SELECT L.LEVNR, L.LEVNAAM, L.LEVSTATUS, V.PRODNR, V. AANKOOPPRIJS FROM LEVERANCIER L, AANKOOPVOORWAARDEN V WHERE L.LEVNR = V.LEVNR; of –SELECT L.LEVNR, L.LEVNAAM, L.LEVSTATUS, V.PRODNR, V.AANKOOPPRIJS FROM LEVERANCIER AS L, INNER JOIN AANKOOPVOORWAARDEN AS V ON (L.LEVNR = V. LEVNR); Select instructie met inner-join (voorbeeld 1)

24

25

26 –Oplossing: SELECT L.LEVNR, L.LEVNAAM, AO.AONR, AO.AODATUM, P.PRODNR, P.PRODNAAM, AOR.BESTELHOEV FROM LEVERANCIER L, AANKOOPORDER AO, AANKOOPORDERREGEL AOR, PRODUCT P WHERE (L.LEVNR = AO. LEVNR) AND (AO.AONR = AOR.AONR) AND (AOR.PRODNR = P.PRODNR); Select instructie met inner-join (voorbeeld 2)

27

28 Het is mogelijk om gegevens te “joinen” die afkomstig zijn uit rijen van eenzelfde tabel. –voor het oplossen van zo’n opdracht moeten twee ‘verschijningsvormen’ van dezelfde tabel onderscheiden worden opdat het systeem de conditie kan onderzoeken waaronder respectieve rijen mogen worden samengevoegd. Gevraagd: geef alle paren van leveranciers die dezelfde vestigingsplaats hebben. Leverancier (levnr, levnaam, levadres, levplaats, levstatus) –SELECT L1.LEVNAAM, L2.LEVNAAM, L1.LEVPLAATS FROM LEVERANCIER L1, LEVERANCIER L2 WHERE L1.LEVPLAATS = L2.LEVPLAATS AND (L1.LEVNR < L2.LEVNR); Select instructie met inner-join (voorbeeld 3)

29 levnrlevnaamlevadreslevplaatslevstatus 05ApersAntwerpen90 02DenulBrussel10 11LauwersLuxemburg92 17HaveneersAntwerpen70 Leverancier L1 L1.LEVNAAML2.LEVNAAML1.LEVPLAATS ApersHaveneersAntwerpen levnrlevnaamlevadreslevplaatslevstatus 05ApersAntwerpen90 02DenulBrussel10 11LauwersLuxemburg92 17HaveneersAntwerpen70 Leverancier L2

30 Samen met de join condities mogen – uiteraard – allerlei andere condities worden opgelegd voor het uiteindelijk selecteren van de rijen. Gevraagd: de namen van de leveranciers die een specifiek product met nummer 1174 kunnen leveren. Leverancier (levnr, levnaam, levadres, levplaats, levstatus) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs, levertermijn) –SELECT L.LEVNAAM FROM LEVERANCIER L, AANKOOPVOORWAARDEN V WHERE L.LEVNR = V.LEVNR AND V.PRODNR = ‘1174’; Select instructie met inner-join (voorbeeld 4)

31 Eventuele overbodige dubbels kunnen steeds met een DISTINCT-optie worden geëlimineerd. Gevraagd: de namen van de leveranciers die tenminste één product kunnen leveren met een groene kleur. –het is mogelijk dat sommige leveranciers meerdere producten met een groene kleur kunnen leveren, maar in overbodige dubbels zijn we niet geïnteresseerd Leverancier (levnr, levnaam,...) Aankoopvoorwaarden (levnr, prodnr,...) Product (prodnr,..., prodkleur) –SELECT DISTINCT L.LEVNAAM FROM LEVERANCIER L, AANKOOPVOORWAARDEN V, PRODUCT P WHERE L.LEVNR = V.LEVNR AND (V.PRODNR = P.PRODNR) AND (P.PRODKLEUR = ‘groen’); Select instructie met inner-join (voorbeeld 5)

32 Gevraagd: geef van alle producten waarvoor bestellingen zijn geplaatst, nummer, naam en totale bestelde hoeveelheid. Product (prodnr, prodnaam, …) Aankooporderregel (aonr, prodnr, bestelhoev) –SELECT P.PRODNR, P.PRODNAAM, SUM(AOR.BESTELHOEV) FROM PRODUCT P, AANKOOPORDERREGEL AOR WHERE P.PRODNR = AOR.PRODNR GROUP BY AOR.PRODNR; Select instructie met inner-join (voorbeeld 6)

33 Met de inner-join zullen rijen die het systeem niet kan samenvoegen, omdat er voor de join-kolommen geen overeenstemmende waarden worden gevonden, niet aanwezig zijn in het eindresultaat. Met de outer-join constructie kan dit probleem worden opgelost. –left-outer-join: elke rij uit de linkertabel wordt behouden in het eindresultaat en - zonodig – aangevuld met null- waarden voor de kolommen die uit de andere tabel komen. –right-outer-join: elke rij uit de rechtertabel wordt behouden –full-outer-join: elke rij uit beide tabellen wordt behouden Select instructie met outer-join

34 Gevraagd: geef nummer, naam en status van alle leveranciers, eventueel tezamen met de nummers van de producten die zij leveren en de aankoopprijs die ze hiervoor aanrekenen. Leverancier (levnr, levnaam,..., levstatus) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs,...) –SELECT L.LEVNR, L.LEVNAAM, L.LEVSTATUS, V.PRODNR, V. AANKOOPPRIJS FROM LEVERANCIER AS L, LEFT OUTER JOIN AANKOOPVOORWAARDEN AS V ON (L.LEVNR = V. LEVNR); Select instructie met left-outer-join (voorbeeld 1)

35

36 Gevraagd: geef van alle producten nummer, naam en totale bestelde hoeveelheid, ook indien er voor een product momenteel geen bestellingen uitstaan. Product (prodnr, prodnaam, …) Aankooporderregel (aonr, prodnr, bestelhoev) –SELECT P.PRODNR, P.PRODNAAM, SUM(AOR.BESTELHOEV) AS SOM FROM PRODUCT AS P, LEFT OUTER JOIN AANKOOPORDERREGEL AS AOR ON (P.PRODNR = AOR.PRODNR) GROUP BY AOR.PRODNR; Select instructie met left-outer-join (voorbeeld 2)

37 Nested queries SELECT... FROM... WHERE... (SELECT... FROM... WHERE... ); Outer block Inner block Als er in een select-instructie geneste select-blokken voorkomen ontstaat er een zogeheten nested query met subquery’s. Het begin van een select-blok wordt met een SELECT component aangegeven.

38 In de where-component van een select-instructie mag als conditie worden gespecificeerd dat de waarde van een gewone expressie (bv. een kolomnaam) vergeleken moet worden met de waarde die door uitvoering van een subquery wordt afgeleverd. Gevraagd: geef de naam van leveranciers bij wie een aankooporder met een bepaald nummer is geplaatst Leverancier (levnr, levnaam, levadres, levplaats, levstatus) Aankooporder (aonr, aodatum, levnr) –SELECT LEVNAAM FROM LEVERANCIER WHERE LEVNR = (SELECT LEVNR FROM AANKOOPORDER WHERE AONR = ‘1079’); Scalaire subqueries (voorbeeld 1)

39 Gevraagd: geef nummer en naam van elk product waarvan de voorraadhoeveelheid hoger is dan die van een bepaald product Product (prodnr, prodnaam, …, hoev_in_voorr) –SELECT PRODNR, PRODNAAM FROM PRODUCT WHERE HOEV-IN-VOORR > (SELECT HOEV-IN-VOORR FROM PRODUCT WHERE PRODNR = ‘0117’); Scalaire subqueries (voorbeeld 2)

40 Select-instructies met IN operator en tabelexpressie. –in de WHERE component van een outer select-blok van een select- instructie mag een IN operator worden gebruikt, gevolgd door een nieuw (inner) select-blok die een tabel-subquery mag zijn. Gevraagd: geef de namen van leveranciers die een specifiek product kunnen leveren Leverancier (levnr, levnaam,..., levstatus) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs,...) –SELECT LEVNAAM FROM LEVERANCIER WHERE LEVNR IN (SELECT LEVNR FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’); Tabel subqueries (voorbeeld 1)

41 Gevraagd: geef de namen van leveranciers die tenminste één product kunnen leveren met een groene kleur Leverancier (levnr, levnaam,...) Aankoopvoorwaarden (levnr, prodnr,...) Product (prodnr,..., prodkleur) –SELECT LEVNAAM FROM LEVERANCIER WHERE LEVNR IN (SELECT LEVNR FROM AANKOOPVOORWAARDEN WHERE PRODNR IN (SELECT PRODNR FROM PRODUCT WHERE PRODKLEUR = ‘GROEN’)); Tabel subqueries (voorbeeld 2)

42 Gevraagd: geef de namen van de producten die zowel door de leverancier met nummer ’01’ als door de leverancier met nummer ’23’ kunnen worden geleverd Aankoopvoorwaarden (levnr, prodnr,...) Product (prodnr, prodnaam,..., prodkleur) –SELECT PRODNAAM FROM PRODUCT WHERE PRODNR IN (SELECT PRODNR FROM AANKOOPVOORWAARDEN WHERE LEVNR = ’05’) AND PRODNR IN (SELECT PRODNR FROM AANKOOPVOORWAARDEN WHERE LEVNR = ’23’); Tabel subqueries (voorbeeld 3)

43 In alle voorgaande gevallen kon de subquery (de inner- select) volledig geëvalueerd worden vooraleer met de verwerking van een outer select-blok werd gestart. –met een gecorreleerde subquery is dat niet zo. Men spreekt van een gecorreleerde subquery wanneer een inner select-blok een kolom bevat die behoort tot een tabel die in een ander outer select-blok is gespecificeerd –de subquery moet telkens opnieuw worden geëvalueerd voor elke rij van de tabel die in het outer select-blok aanwezig is. Gecorreleerde subqueries

44 Gevraagd: geef de nummers van de producten waarvoor er tenminste twee bestellingen uitstaan. Product (prodnr, prodnaam, …) Aankooporderregel (aonr, prodnr, bestelhoev) –SELECT P.PRODNR FROM PRODUCT P WHERE 1 < (SELECT COUNT (*) FROM AANKOOPORDERREGEL AOR WHERE P.PRODNR = AOR.PRODNR); Gecorreleerde subqueries (voorbeeld 1)

45 Gevraagd: geef van de leveranciers die producten kunnen leveren tegen een prijs die lager ligt dan de gemiddelde prijs van dat product, nummer en naam, tezamen met nummer en naam van de betreffende producten, de prijs die door de leverancier wordt aangerekend en de levertermijn. Leverancier (levnr, levnaam,...) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs, levertermijn) Product (prodnr, prodnaam,... ) –SELECT L.LEVNR, L.LEVNAAM, P.PRODNR, P.PRODNAAM, V1.AANKOOPPRIJS, V1.LEVERTERMIJN FROM LEVERANCIER L, AANKOOPVOORWAARDEN V1, PRODUCT P WHERE L.LEVNR = V1.LEVNR AND V1.PRODNR = P.PRODNR AND V1.AANKOOPPRIJS < (SELECT AVG(AANKOOPPRIJS) FROM AANKOOPVOORWAARDEN V2 WHERE P.PRODNR = V2.PRODNR) ORDER BY L.LEVNR; Gecorreleerde subqueries (voorbeeld 2)

46

47 Gevraagd: geef de drie hoogste productnummers uit de producttabel. –Redenering: het hoogste productnummer: er is geen enkel product met hoger nummer het tweede hoogste productnummer: er is één product met een hoger nummer het derde hoogste productnummer: er zijn twee producten met een hoger nummer. –Werkwijze: Voor ieder product tellen wij het aantal producten met een hoger nummer; als dit aantal kleiner is dan 3, dan behoort het nummer tot de drie hoogste nummers. –Oplossing: SELECT P1.PRODNR FROM PRODUCT P1 WHERE 3 > (SELECT COUNT (*) FROM PRODUCT P2 WHERE P1.PRODNR < P2.PRODNR); Gecorreleerde subqueries (voorbeeld 3)

48 Nested queries met ALL of ANY In de WHERE component van het (outer) select-blok van een select- instructie mag een ALL operator of een ANY operator worden gebruikt, die gevolgd wordt door een (inner) select-blok. –de ALL operator genereert een ‘waar-antwoord’ als aan de conditie is voldaan voor alle waarden die, na uitvoering van de subquery, zijn verkregen. als de subquery geen waarde oplevert, evalueert de gehele conditie als ‘waar’. –de ANY operator genereert een ‘waar-antwoord’ als aan de conditie is voldaan voor tenminste één van de waarden die, na uitvoering van de subquery, zijn verkregen. als de subquery geen waarde oplevert, evalueert de gehele conditie als ‘niet-waar’ Een conditie van de vorm =ANY(…) is equivalent aan het gebruik van de IN operator.

49 Gevraagd: geef de namen van de leveranciers die de hoogste prijs aanrekenen voor een bepaald product. Leverancier (levnr, levnaam,...) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs, levertermijn) –Oplossing: SELECT LEVNAAM FROM LEVERANCIER WHERE LEVNR IN (SELECT LEVNR FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘1245’ AND AANKOOPPRIJS ≥ ALL (SELECT AANKOOPPRIJS FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘1245’)); Nested queries met ALL (voorbeeld 1)

50

51 Gevraagd: geef nummer en naam van elke leverancier waarvan de evaluatiecode het hoogst is van alle leveranciers die in zijn gemeente zijn gevestigd. –Redenering: Als een leverancier in dezelfde plaats is gevestigd als één of meer andere leveranciers en zijn evaluatiecode (= levstatus) is beter of minstens gelijk aan die van alle (andere) leveranciers uit dezelfde plaats dan voldoet deze leverancier aan de voorwaarde. –Oplossing: SELECT L1.LEVNR, L1.LEVNAAM, L1.LEVSTATUS FROM LEVERANCIER L1 WHERE L1.LEVSTATUS ≥ ALL (SELECT L2.LEVSTATUS FROM LEVERANCIER L2 WHERE L1.LEVPLAATS = L2.LEVPLAATS); Nested queries met ALL (voorbeeld 2)

52 Gevraagd: geef de namen van de leveranciers die niet de laagste prijs aanrekenen voor een bepaald product. –Redenering: vanaf het moment dat de aankoopprijs van een product bij een bepaalde leverancier hoger is dan de prijs van dit product bij tenminste één andere leverancier is aan de voorwaarde van de vraag voldaan. –Oplossing: SELECT LEVNAAM FROM LEVERANCIER WHERE LEVNR IN (SELECT LEVNR FROM AANKOOPVOORWAARDEN WHERE AANKOOPPRIJS > ANY (SELECT AANKOOPPRIJS FROM AANKOOPVOORWAARDEN WHERE PRODNR = ‘0117’)); Nested queries met ANY (voorbeeld)

53 De EXISTS operator wordt gebruikt om te controleren of het resultaat van de uitvoering van een gecorreleerde subquery wel of niet leeg is. –vanaf het ogenblik dat de subquery minstens één rij oplevert, evalueert de conditie naar ‘waar’. –als de subquery geen rijen oplevert, evalueert de conditie naar ‘niet-waar’. Omdat tijdens de evaluatie van de conditie met EXISTS operator enkel gekeken wordt of het resultaat van de uitvoering van een subquery wel of niet rijen oplevert, is het onbelangrijk wat in de select-component van de subquery staat gespecificeerd –meestal gebruikt men de vorm: SELECT *. Gecorreleerde subqueries met EXISTS

54 Gevraagd: geef de namen van de leveranciers die een specifiek product kunnen leveren (reeds voorheen anders opgelost) Leverancier (levnr, levnaam,...) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs, …) –SELECT LEVNAAM FROM LEVERANCIER L WHERE EXISTS (SELECT * FROM AANKOOPVOORWAARDEN V WHERE L.LEVNR = V.LEVNR AND V.PRODNR = ‘0117’); Gecorreleerde subqueries met EXISTS (voorbeeld 1)

55 Gevraagd: geef naam, adres en gemeente van de leveranciers die alle producten kunnen leveren –Redenering: geef naam, adres en gemeente van de leveranciers waarvoor er geen enkel product bestaat dat zij niet kunnen leveren –Oplossing: SELECT LEVNAAM, LEVADRES, LEVPLAATS FROM LEVERANCIER L WHERE NOT EXISTS (SELECT * FROM PRODUCT P WHERE NOT EXISTS (SELECT * FROM AANKOOPVOORWAARDEN V WHERE L.LEVNR = V.LEVNR AND P.PRODNR = V.PRODNR)); Gecorreleerde subqueries met EXISTS (voorbeeld 2)

56 Subqueries: overzicht van de operatoren scalaire subquery-expressie: –vergelijkingsoperatoren (, >, =) tabel subquery-expressie –IN operator –EXISTS operator –ALL operator in combinatie met vergelijkingsoperator (, =,...) –ANY operator in combinatie met vergelijkingsoperator (, =,...)

57 In de SELECT component mag een scalaire subquery voorkomen Gevraagd: geef van alle producten nummer, naam en totale bestelde hoeveelheid, ook indien er voor een product momenteel geen bestellingen uitstaan. Product (prodnr, prodnaam, …) Aankooporderregel (aonr, prodnr, bestelhoev) –Oplossing: SELECT P.PRODNR, P.PRODNAAM, (SELECT SUM(BESTELHOEV) FROM AANKOOPORDERREGEL AOR WHERE P.PRODNR = AOR.PRODNR) AS SOM FROM PRODUCT P Vergelijk met left-outer-join (voorbeeld 2) Scalaire subquery in de SELECT component

58 Het resultaat van een tabel subquery is een tabel, die zelf weer in een FROM component mag gebruikt worden Gevraagd: geef de nummers van de producten waarvan het verschil tussen maximum en minimumprijs meer dan 100 euro bedraagt. Aankoopvoorwaarden (levnr, prodnr, aankoopprijs, …) –Oplossing: SELECT PRODNR, MINPRIJS, MAXPRIJS FROM (SELECT PRODNR, MIN(AANKOOPPRIJS), MAX(AANKOOPPRIJS) FROM AANKOOPVOORWAARDEN GROUP BY PRODNR) AS PRIJSMARGE(PRODNR, MINPRIJS, MAXPRIJS) WHERE MAXPRIJS – MINPRIJS > 100 Tabel subquery in de FROM component

59 Queries met gebruik van setoperatoren In SQL is het mogelijk om select-blokken met behulp van setoperatoren te combineren. –UNION: elke rij die in het resultaat van één van de select-blokken voorkomt (of in het resultaat van beide), komt in het eindresultaat –INTERSECT: enkel rijen die in het resultaat van beide select-blokken voorkomen, komen in het eindresultaat –EXCEPT: in het eindresultaat komen enkel de rijen die in het eerste blok aanwezig zijn maar niet in het tweede blok In de relationele algebra komen deze operatoren overeen met: unie, doorsnede en verschil Dubbele rijen worden automatisch uit het eindresultaat verwijderd, tenzij de optie ALL zou zijn gebruikt. –UNION ALL –INTERSECT ALL –EXCEPT ALL

60 Gevraagd: geef nummer en naam van de leveranciers die in een bepaalde stad gevestigd zijn, of een specifiek product kunnen leveren (of aan beide voorwaarden tegelijk voldoen) Leverancier (levnr, levnaam,..., levplaats) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs, …) –Oplossing: SELECT LEVNR, LEVNAAM FROM LEVERANCIER WHERE LEVPLAATS = ‘BRUSSEL’ UNION SELECT LEVNR, LEVNAAM FROM LEVERANCIER L, AANKOOPVOORWAARDEN V WHERE L.LEVNR = V.LEVNR AND V.PRODNR = ‘0117’ ORDER BY LEVNAAM ASC; –Bemerk: een eventuele sortering wordt op het eindresultaat toegepast (ORDER BY volgt achter het laatste select blok) Queries met setoperatoren: UNION (voorbeeld)

61 Gevraagd: geef nummer en naam van de leveranciers die in een bepaalde stad gevestigd zijn én een specifiek product kunnen leveren Leverancier (levnr, levnaam,..., levplaats) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs, …) –Oplossing: SELECT LEVNR, LEVNAAM FROM LEVERANCIER WHERE LEVPLAATS = ‘BRUSSEL’ INTERSECT SELECT LEVNR, LEVNAAM FROM LEVERANCIER L, AANKOOPVOORWAARDEN V WHERE L.LEVNR = V.LEVNR AND V.PRODNR = ‘0117’ ORDER BY LEVNAAM ASC; Queries met setoperatoren: INTERSECT (voorbeeld)

62 Gevraagd: geef het nummer van de leveranciers die momenteel geen producten kunnen leveren Leverancier (levnr, levnaam,..., levplaats) Aankoopvoorwaarden (levnr, prodnr, aankoopprijs, levertermijn) –Oplossing: SELECT LEVNR FROM LEVERANCIER EXCEPT SELECT LEVNR FROM AANKOOPVOORWAARDEN; Queries met setoperatoren: EXCEPT (voorbeeld)

63 Voorbeeld: Voetbaldatabase AFDELINGEN ( RANGSMALLINTNOT NULL, AANTAL_STIJGERSSMALLINT, AANTAL_DALERSSMALLINT, PRIMARY KEY( RANG ) ); PLOEGEN ( STAMNUMMERINTEGERNOT NULL, AANSLUITINGSJAARINTEGER, NAAMCHAR(30), STRAATCHAR(50), HUISNUMMERSMALLINT, POSTCODEINTEGER, GEMEENTECHAR(50), TELEFOONINTEGER, CLUB_EMBLEEMBLOB, AFDELINGSMALLINT,refereert aan AFDELINGEN GEWONNEN SMALLINT, (aantal gewonnen wedstrijden) VERLOREN SMALLINT,(aantal verloren wedstrijden) GELIJKSMALLINT,(aantal gelijk gespeelde wedst) SCORE_VOORSMALLINT,(totaal # doelpunten voor) SCORE_TEGENSMALLINT,(totaal # doelpunten tegen) PRIMARY KEY(STAMNUMMER) );

64 STADIA ( NAAMCHAR(30)NOT NULL, AANTAL_PLAATSENINTEGER, PLOEGINTEGERNOT NULL,refereert aan PLOEGEN PRIMARY KEY(NAAM) ); SPELERS ( BONDSNUMMERINTEGERNOT NULL, FAMILIENAAMCHAR(30)NOT NULL, VOORNAAMCHAR(30)NOT NULL, NATIONALITEITCHAR(30), STRAATCHAR(50), HUISNUMMERSMALLINT, POSTCODEINTEGER, GEMEENTECHAR(50), LANDCHAR(50), TELEFOONINTEGER, PLOEGINTEGERNOT NULL,refereert aan PLOEGEN PRIMARY KEY(BONDSNUMMER) ); SPONSORS ( NAAMCHAR(30)NOT NULL, BUDGETINTEGER, PLOEGINTEGERNOT NULL,refereert aan PLOEGEN PRIMARY KEY(NAAM) );

65 WEDSTRIJDEN ( NUMMERINTEGERNOT NULL, AFDELINGSMALLINTNOT NULL,refereert aan AFDELINGEN SPEELDAGSMALLINTNOT NULL, DATUMDATENOT NULL, TIJDTIME, THUISPLOEGINTEGERNOT NULL,refereert aan PLOEGEN BEZOEKERSINTEGERNOT NULL,refereert aan PLOEGEN SCORE_THUISPLOEGSMALLINT, SCORE_BEZOEKERSSMALLINT, SCHEIDSRECHTERINTEGERNOT NULL,refereert aan RECHTERS LIJNRECHTER1INTEGERNOT NULL,refereert aan RECHTERS LIJNRECHTER2INTEGERNOT NULL,refereert aan RECHTERS PRIMARY KEY(NUMMER) ); SELECTIES ( SPELERINTEGERNOT NULL, refereert aan SPELERS WEDSTRIJDINTEGERNOT NULL, refereert aan WEDSTRIJDEN SCORESMALLINTNOT NULL, STRAFPUNTENSMALLINTNOT NULL, PRIMARY KEY(SPELER,WEDSTRIJD) );

66 TRAINERS ( BONDSNUMMER INTEGERNOT NULL, FAMILIENAAM CHAR(30)NOT NULL, NAAMCHAR(30)NOT NULL, (voornaam van de trainer) NATIONALITEIT CHAR(30), STRAATCHAR(50), HUISNUMMERSMALLINT, POSTCODEINTEGER, GEMEENTECHAR(50), LANDCHAR(50), TELEFOONINTEGER, PLOEGINTEGERNOT NULL, refereert aan PLOEGEN PRIMARY KEY(BONDSNUMMER) ); RECHTERS ( NUMMERINTEGERNOT NULL, FAMILIENAAMCHAR(50)NOT NULL, VOORNAAMCHAR(30)NOT NULL, STRAATCHAR(50), HUISNUMMERSMALLINT, POSTCODEINTEGER, GEMEENTECHAR(50), TELEFOONINTEGER, PRIMARY KEY(NUMMER) );

67 Voetbaldatabase: overzicht


Download ppt "Hoofdstuk 8: Werken met SQL voor eindgebruikers. Overzicht Inleiding op SQL: de select-instructie Eenvoudige queries Join queries Nested queries Queries."

Verwante presentaties


Ads door Google