Rekurzív nem-negált Datalog és SQL3 WITH RECURSIVE
PL/SQL alapok, feladatok

     
> Papíros feladatok:
   >> 2.7. Rekurzív Datalog és rekurzió az SQL-ben

> Gépes feladatok: III. témakör: PL/SQL programozás
   >> 3.1. PL/SQL alapok, változóhasználat, vezérlési szerkezetek
   >> 3.2. PL/SQL SELECT INTO, hivatkozási és összetett adattípusok
   >> folyt.köv.héten 3.3. PL/SQL kurzor és 3.4. eljárások és függvények
   
2.7. Rekurzív nem-negált Datalog és SQL3 WITH RECURSIVE
   
Datalog: [Ullman-Widom]  5.3-5.4. Datalog szabályok és lekérdezések
>> lásd az előadás anyagát Datalog (jelszóval)
>> és a múlt heti feladatokat: 2.6. Lekérdezések kifejezése Datalogban
    
Rekurzió: [Ullman-Widom] 10.2. Rekurzió az SQL-ben (466-474.o.)
>>lásd az előadás anyagát Rek.Datalog, Rek.SQL (jelszóval)
   
Rek1.feladat:
- Az alábbi feladat a tankönyv (Ullman-Widom kék könyv) 10.2 szakaszára épül.
  Jaratok(legitarsasag, honnan, hova, koltseg, indulas, erkezes)
  táblában repülőjáratok adatait tároljuk.
- Készítsünk ebből saját példányt: jaratok_tabla.txt és az alapján dolgozzunk
            DROP TABLE jaratok;
            CREATE TABLE jaratok(
                            legitarsasag CHAR(2),
                            honnan VARCHAR2(10),
                            hova VARCHAR2(10),
                            koltseg NUMBER,
                            felszallas NUMBER,
                            erkezes NUMBER);
      
            INSERT INTO jaratok VALUES('UA', 'SF','DEN', 1000, 930,1230);
            INSERT INTO jaratok VALUES('AA', 'SF','DAL', 10000, 900,1430);
            INSERT INTO jaratok VALUES('UA','DEN','CHI', 500, 1500,1800);
            INSERT INTO jaratok VALUES('AA','DEN','DAL', 2000, 1400,1700);
            INSERT INTO jaratok VALUES('AA','DAL','CHI', 600, 1530,1730);
            INSERT INTO jaratok VALUES('AA','DAL', 'NY', 2000, 1500,1930);
            INSERT INTO jaratok VALUES('AA','CHI', 'NY', 3000, 1900,2200);
            INSERT INTO jaratok VALUES('UA','CHI', 'NY', 2000, 1830,2130);

- (Papíros feladat) Fejezzzük ki Datalog programmal, hogy mely (x,y) város párokra
   lehetséges egy vagy több átszállással eljutni x városból y városba?
- Megoldás:
   1.    Eljut(X, Y) <- Jaratok(L, X, Y, K, F, E)
   2.    Eljut(X, Y) <- Eljut(X, Z) AND Jaratok(L, Z, Y, K, F, E)

- (Papíros feladat) A fenti rekurzív Datalog programot írd át az SQL3 szabványban
   szereplő WITH RECURSIVE utasítással! (Csak papíron! Oracle nem támogatja).
- Megoldás:
            WITH RECURSIVE eljut AS
                  (SELECT honnan, hova FROM jaratok
             UNION
                  SELECT eljut.honnan, jaratok.hova
                  FROM eljut, jaratok
                  WHERE eljut.hova = jaratok.honnan)
            SELECT * FROM eljut;
       
- (Gépes feladatok: Oracle CONNECT BY PRIOR, lásd előző órán 8.gyak#2.5.)
   Amennyiben azt szeretnénk megtudni, hogy mely városokba lehet eljutni Dallasból
   ezt a következő hierarchikus lekérdezéssel kapjuk meg ('DAL'='Dallas')
            SELECT DISTINCT hova
            FROM jaratok
            WHERE HOVA <> 'DAL'
            START WITH honnan = 'DAL'
            CONNECT BY PRIOR hova = honnan;

- Most szúrjunk be még egy sort, ami után már irányított kör is lesz a táblában:
            INSERT INTO jaratok VALUES('LH', 'CHI', 'DEN', 2000, 1900, 2100);
   Ekkor a fenti hierarchikus lekérdezés nem működik, viszont NOCYCLE-lel igen:
            SELECT DISTINCT hova
            FROM jaratok
            WHERE HOVA <> 'DAL'
            START WITH honnan = 'DAL'
            CONNECT BY NOCYCLE PRIOR hova = honnan;
 
- Átszállásokkal mely városokba lehet eljutni San Franciscoból ('SF'='San Francisco')
            SELECT LPAD(' ', 4*level) ||honnan, hova, level-1 Atszallasok
            FROM jaratok
            WHERE HOVA <> 'SF'
            START WITH honnan = 'SF'
            CONNECT BY NOCYCLE PRIOR hova = honnan;
   
- A hierarchikus lekérdezésben további pszeudo oszlopokat is használhatunk, amint
   azt az alábbi példában láthatjuk az úzvonal megadását
           SELECT hova, sys_connect_by_path(honnan||'->'||hova, '/'),
                          connect_by_isleaf, connect_by_iscycle
           FROM jaratok
           START WITH honnan = 'SF'
           CONNECT BY NOCYCLE PRIOR hova = honnan;
   
- Mely (x, y) várospárokra lehetséges egy vagy több átszállással eljutni x városból y városba?
   Ezt PL/SQL programmal fogjuk Oracle-ben megoldani (folytatjuk, lásd 11.gyak#Rek1)
   

3.1. PL/SQL alapok, változóhasználat, vezérlési szerkezetek

SEGÉDANYAGOK: ORACLE  PL/SQL:
Oracle® Database 11g Release 2 Documentation Library
- Oracle PL/SQL Language Reference 11gR2         HTML   PDF
- Oracle PL/SQL Packages and Types Ref.11gR2  HTML   PDF
 
További segédanyagok a PL/SQL-hez:
- Nikovits Tibor (ELTE) PL/SQL összefoglaló: NT_Plsql.htm
- Kósa Balázs (ELTE) PL/SQL összefoglaló: KB_Plsql.pdf   
- Ullman/Chang (Standford) Using Oracle PL/SQL
- Ullman/Chang (Standford) Constraints and Triggers
- PL/SQL Technology Center (Oracle 11g PL/SQL)
     
Változóhasználat: 
1a_valtozok.sql - Változóhasználat (I. az SQL*Plus felhasználói változói,
      II. az SQL*Plus környezeti változói, III. a PL/SQL (belső) változói).
      Az adatok képernyőre való kiíratása (Az Oracle beépített csomagjai,  
      DBMS_OUTPUT csomag PUT_LINE eljárása). CONCAT fv. vagy || jel.
--   Írjunk egy PL/SQL blokkot tartalmazó SQL*Plus szkipt programot, amely
      a felhasználótól bekér egy egész számot! Ha ez a szám nagyobb 100-nál,
      akkor a PL/SQL blokkban, egyébként pedig a PL/SQL blokkot követő
      gazdanyelvi (SQL*Plus) környezetben írassa ki
 
1b_select_into.sql - A SELECT ... INTO utasítás a PL/SQL-ben
--   Határozzuk meg egy PL/SQL program segítségével a felhasználó által
      megadott telephelyen dolgozók béröszegét. A telephelynek a várost (loc)
      adjuk meg (mint például Boston, Chicaco, Dallas vagy New York).
--   Ennek a feladatnak további megoldásaira a következő szakaszban
      visszatérünk (lásd 2a_select_into.sql és további megoldásait is). 

Vezérlési szerkezetek:
-- A programozási nyelvekből ismert egyszerű példák
1c_if_then.sql - Feltételes utasítás (két egész szám összege páros-e)
1d_loop_ciklus.sql - LOOP ciklus (a Fibonacci-sorozat elemei) 
1e_while_ciklus.sql - WHILE ciklus (az Euklideszi algoritmus)
1f_for_ciklus.sql - FOR ciklus (páratlan számok négyzetösszege)
      

3.2. SELECT INTO, hivatkozási és összetett adattípusok
-- Példák plsql_peldak.sql

2a_select_into.sql - A SELECT ... INTO utasítás a PL/SQL-ben
--   Határozzuk meg egy PL/SQL program segítségével a felhasználó által
      megadott telephelyen dolgozók béröszegét. A telephelynek a várost (loc)
      adjuk meg (mint például Boston, Chicaco, Dallas vagy New York).
--   Lásd a korábbi 1b_select_into feladat I.megoldását is, csak most
      hivatkozási típus deklarálásával oldjuk meg a feladatot! II.megoldás:
      Közvetlen összegzéssel. III.mo: Tagonkénti összesítéssel (nézettáblával).
--   Valamint rejtett kurzorral való másik megoldására még visszatérünk. 

2b_gyujtotabla.sql - Összetett típus, rekord, gyűjtőtábla
-    Írjunk PL/SQL programot, amely meghatározza a 7698 azonosítójú
     dolgozó nevét gyűjtőtábla használatával.  
        
>> folyt.köv.héten 3.3. PL/SQL kurzor és 3.4. eljárások és függvények


PL/SQL FELADATOK:
-- Táblák és az eddigi sql feladatok: table_dolgozo.txt 
-- Ehhez a táblák létrehozása: create_dolgozo.txt

1.) Hello World program (alap program, kiírás a képernyőre)

2.) Írjuk ki KING fizetését (olvasás táblából változóba)

3.) Írjuk ki KING belépési dátumát és fizetését különböző
     formátumokban 1981.11.17, 1981-november-17, stb
     (dátum formátumok, több oszlopos lekérdezés)
   

További gyakorló feladatok találhatóak az Oracle Példatárban
--  Lásd Feladatok.pdf (8-9.fejezet feladatai)  
-- Ehhez: a táblák létrehozása  cr_dept_emp.sql
              
Vissza az AB1 gyakorlat oldalára             Vissza a Kezdőlapra