(Microsoft PowerPoint - TBD_ns_w5.ppt [tryb zgodno\234ci])
Transkrypt
(Microsoft PowerPoint - TBD_ns_w5.ppt [tryb zgodno\234ci])
Materiały Materiały dostępne są na stronie: Technologie baz danych aragorn.pb.bialystok.pl/~gkret Wykład 5: Kursory jawne. Podprogramy. Małgorzata Krętowska Wydział Informatyki Politechnika Białostocka 1 2 Plan wykładu Kursory • Kursory niejawne – powtórzenie • Kursory jawne • Podprogramy: funkcje, procedury, pakiety Kursory niejawne Kursory jawne • deklarowane są dla wszystkich instrukcji DML oraz SELECT • deklarowane przez programistę • PL/SQL zarządza automatycznie kursorem niejawnym • Parametry kursora: Nazwa_kursora%nazwa_parametru • Parametry kursora: SQL%nazwa_parametru 3 4 Atrybuty kursora SQL SQL%ROWCOUNT SQL%FOUND Atrybuty kursorów - przykład Liczba wierszy, których dotyczyła ostatnia instrukcja SQL DECLARE v_usuniete VARCHAR2(30); Atrybut logiczny, który przyjmuje wartość TRUE, gdy ostatnia instrukcja dotyczyla jednego lub więcej wierszy SQL%NOTFOUND Atrybut logiczny, który przyjmuje wartość TRUE, gdy ostatnia instrukcja dotyczyła zerowej liczby wierszy SQL%ISOPEN Zawsze przyjmuje wartość FALSE ponieważ PL/SQL zamyka kursory natychmiast po ich wykonaniu BEGIN DELETE FROM zamowiona_ksiazka WHERE id_zamowienia = ∥ v_usuniete := TO_CHAR(SQL%ROWCOUNT) || ‘rekordow usunietych.’; END; Kursory niejawne - przykład Przykład cd DECLARE v_liczba NUMBER; v_nazwa VARCHAR2(15); BEGIN CREATE TABLE komunikat (numer NUMBER, tekst1 VARCHAR2(15), tekst2 VARCHAR2(15) ); SELECT COUNT(*), nazwa INTO v_liczba, v_nazwa FROM t_wydawca, t_ksiazka WHERE t_wydawca.id_wydawcy=t_ksiazka.wydawca AND id_wydawcy =1 GROUP BY nazwa,ID_WYDAWCY; INSERT INTO komunikat (numer,tekst1) VALUES (v_liczba, v_nazwa); END; / Przykład: Napisać blok PL/SQL, który sprawdzi ile książek wydał wydawca o identyfikatorze = 1. Nazwę wydawcy oraz liczbę książek należy zapisać w tabeli komunikat. 7 8 Kursory jawne - deklaracja Kursory jawne DECLARE ….. ; CURSOR nazwa_kursora [(parametr [, parametr] … )] IS instrukcja_select; parametr ::= nazwa_parametru typ danych [{:= | DEFAULT wyrażenie}] OPEN nazwa_kursora [(parametr [, parametr] ...)]; FETCH nazwa_kursora INTO zmienna [ , zmienna ...]; CURSOR kursor (p_isbn VARCHAR(10)) IS SELECT * FROM ksiazka WHERE isbn = p_isbn; CLOSE nazwa_kursora; Sterowanie kursorami jawnymi NIE DECLARE OPEN FETCH PUSTY? TAK CLOSE DECLARE CURSOR k_cursor IS SELECT * FROM zamowiona_ksiazka WHERE isbn = 1; k_record zamowiona_ksiazka%ROWTYPE; v_ilosc zamowiona_ksiazka. ilosc %TYPE := 0; BEGIN OPEN k_cursor; LOOP FETCH k_cursor INTO k_record; IF k_cursor%NOTFOUND THEN EXIT; END IF; v_ilosc := v_ilosc + k_record.ilosc; END LOOP; dbms_output.put_line(k_cursor%ROWCOUNT); dbms_output.put_line(v_ilosc); CLOSE k_cursor; END; Pęta kursorowa FOR Kursory jawne - przykład FOR nazwa_rekordu IN nazwa_kursora LOOP instrukcja-1; instrukcja-2; ……. END LOOP; Niejawne instrukcje OPEN, FETCH, CLOSE zmienna nazwa_rekordu – zadeklarowana niejawnie Kursor w pętli FOR DECLARE CURSOR a_cursor IS SELECT * FROM autor; BEGIN FOR i IN a_cursor LOOP dbms_output.put_line(i.nazwisko); END LOOP; END; BEGIN FOR i IN (SELECT * FROM autor) LOOP dbms_output.put_line(i.nazwisko); END LOOP; END; DECLARE CURSOR k_cursor (p_zam zamowienie.id_zamowienia%TYPE) IS SELECT * FROM zamowiona_ksiazka WHERE id_zamowienia = p_zam; BEGIN FOR i IN k_cursor(1) LOOP dbms_output.put_line(i.isbn); END LOOP; END; Atrybuty kursorow jawnych %ROWCOUNT Liczba wierszy, sprawdzonych w kursorze w danym momencie %FOUND Atrybut logiczny, który przyjmuje wartość TRUE, jeśli instrukcja FETCH zwróci wiersz %NOTFOUND Atrybut logiczny, który przyjmuje wartość TRUE, jeśli ostatnia instrukcja FETCH nie zwrócila żadnego wiersza %ISOPEN Atrybut logiczny, który przyjmuje wartość TRUE, jeśli kursor jest otwarty Użycie klauzuli WHERE CURRENT OF DECLARE CURSOR k_cursor(v_zakres ksiazka.cena%TYPE) IS SELECT cena FROM ksiazka WHERE cena > v_zakres FOR UPDATE; BEGIN FOR i IN k_cursor(40) LOOP UPDATE ksiazka SET cena = cena* 1.1 WHERE CURRENT OF k_cursor; END LOOP; COMMIT; END; Użycie klauzuli WHERE CURRENT OF • Używając kursorów można aktualizować lub usuwać rekordy • Klauzula FOR UPDATE blokuje wiersze • Klauzula WHERE CURRENT OF odwołuje się do bieżącego rekordu z kursora jawnego • Nie wolno zatwierdzać instrukcji z kursora jawnego, jeżeli użyta jest klauzula FOR UPDATE Kursory - podsumowanie Podprogramy • Kursory niejawne używane dla wszystkich instrukcji DML oraz zapytań zwracających jeden wiersz • Procedury do przeprowadzenia akcji • Funkcje do obliczania wartości • Pakiety do gromadzenia logicznie powiązanych procedur i funkcji • Kursory jawne używane dla zapytań zwracających zero lub więcej wierszy Podprogramy Składniki podprogramu Nagłówek podprogramu [deklaracje] BEGIN [EXCEPTION obsługa wyjątków] [CREATE OR REPLACE] PROCEDURE nazwa_procedury [ (parametr [, parametr … ] )] IS [deklaracje] BEGIN [EXCEPTIONS obsługa wyjątków] END [nazwa_procedury]; END; Podprogramy [CREATE OR REPLACE] FUNCTION nazwa_funkcji [(parametr [, parametr … ] )] RETURN nazwa_typu IS [deklaracje] BEGIN [EXCEPTIONS obsługa wyjątków] END [nazwa_funkcji]; Tryby parametrów podprogramów Argument IN Środowisko Argument OUT Argument IN OUT [deklaracje] BEGIN [EXCEPTION obsługa wyjątków] END; Parametry w podprogramach parametr [IN | OUT [NOCOPY] | IN OUT [NOCOPY]] typ_danych [:= | DEFAULT wyrazenie] IN Parametry przekazywane przez wartość OUT Parametry przekazywane przez referencję IN OUT Procedura - przykład CREATE OR REPLACE PROCEDURE mod_cene (p_isbn ksiazka.isbn%TYPE, p_wartosc NUMBER) IS BEGIN UPDATE ksiazka SET cena = cena + p_wartosc WHERE isbn = p_isbn; END mod_cene; Funkcja - przykład Wywoływanie procedur/funkcji CREATE OR REPLACE FUNCTION wyznacz_VAT(p_isbn ksiazka.isbn%TYPE) RETURN NUMBER IS EXECUTE nazwa_procedury[(parametry)] v_cena ksiazka.cena%TYPE; BEGIN SELECT cena INTO v_cena FROM ksiazka WHERE isbn = p_isbn; RETURN (v_cena*0.07); END wyznacz_VAT; EXECUTE zmienna:= nazwa_funkcji[(parametry)] Wywoływanie procedur/funkcji - przykład Użycie funkcji w instrukcji SQL EXECUTE mod_cene(1, 5); SELECT tytul, cena, wyznacz_VAT(1) FROM ksiazka VARIABLE g_vat NUMBER EXECUTE :g_vat := wyznacz_VAT(1); PRINT g_vat Błędy • Błędy bloków anonimowych pojawiają się na ekranie • Błędy zapamiętanych procedur są zapisywane w tabeli USER_ERRORS słownika danych SHOW ERRORS SELECT * FROM user_errors; WHERE isbn = 1; Procedury/funkcje -podsumowanie • Funkcje zdefiniowane przez użytkownika mogą być stosowane w instrukcjach SQL (procedury nie!) • Funkcja nie może zawierać instrukcji DML Pakiety Specyfikacja pakietu Baza danych Aplikacja Pakiet Specyfikacja Ciało pakietu Tworzenie ciala pakietu CREATE [ OR REPLACE ] PACKAGE BODY nazwa_pakietu AS deklaracje prywatne definicje podprogramów [ BEGIN instrukcje inicjalizujące pakietu] END; CREATE [OR REPLACE] PACKAGE nazwa_pakietu AS deklaracje publiczne specyfikacje podprogramów END; Pakiety - przykład CREATE OR REPLACE PACKAGE pak_zamowienia AS PROCEDURE usun_zamowienie (v_id zamowienie.id_zamowienia%TYPE); PROCEDURE dodaj_pozycje (v_id zamowienie.id_zamowienia%TYPE, v_isbn ksiazka.isbn%TYPE, v_ilosc zamowiona_ksiazka.ilosc%TYPE); END; Pakiety - przykład CREATE PACKAGE BODY pak_zamowienia AS PROCEDURE usun_zamowienie (v_id zamowienie.id_zamowienia%TYPE) IS BEGIN DELETE FROM zamowiona_ksiazka WHERE id_zamowienia = v_id; DELETE FROM zamowienie WHERE id_zamowienia = v_id; END; Pakiety - przykład PROCEDURE dodaj_pozycje (v_id zamowienie.id_zamowienia%TYPE, v_isbn ksiazka.isbn%TYPE, v_ilosc zamowiona_ksiazka.ilosc%TYPE); IS BEGIN INSERT INTO zamowiona_ksiazka VALUES(v_id, v_isbn, SYSDATE, v_ilosc); END; END; -- koniec pakietu Pakiety - przykład EXECUTE pak_zamowienia.usun_zamownienie(5); EXECUTE pak_zamowienia.dodaj_pozycje(,,,); Pakiety - zalety korzystania • Poprawa zarządzania procedurami i funkcjami • Poprawa bezpieczeństwa (uprawnienia do pakietu!) • Poprawa efektywności