Plan wykładu PL/SQL PL/SQL - historia

Transkrypt

Plan wykładu PL/SQL PL/SQL - historia
Plan wykładu
2
Wprowadzenie do PL/SQL
Bloki
Podstawowe składowe języka
Zmienne i stałe
Kursory
TWORZENIE APLIKACJI BAZODANOWYCH
Wykład 2: Wprowadzenie do PL/SQL: bloki
anonimowe, zmienne, kursory
Małgorzata Krętowska
Wydział Informatyki
Politechnika Białostocka
PL/SQL
3
PL/SQL - historia
4
PL/SQL (Procedural Language SQL)
Proceduralne (a czasem obiektowe) rozszerzenie
programistyczne
języka
SQL,
stworzone,
udostępnione przez Oracle i przeznaczone do
obsługi narzędzi tej firmy
Wywodzi się z języka ADA
Jest chroniony prawami autorskimi,
Jest językiem trzeciej generacji 3GL,
PL/SQL 1.0 wprowadzono w 1991 roku, wersja była
ograniczona i brakowało w niej wielu funkcji,
wypuszczona z wersją serwera bazodanowego 6.0,
Kolejna wersja 2.3 udostępniała obsługę procedur i
funkcji składowanych,
Wersja 8.0 – wprowadzenie modelu obiektoworelacyjnego,
Wersje 8.1, 9.0, 9.2, 10.0 to kolejne udoskonalenia
języka,
Najnowsza wersja to 11.0
Bloki
5
Struktura bloku
6
Podstawowa jednostka w PL/SQL
Program składa się przynajmniej z jednego bloku
Bloki mogą być zagnieżdżone
Bloki mogą być wykonywane tylko raz, bez
zapisywania (bloki anonimowe)
Bloki można zapisywać w bazie w celu ich
późniejszego wykorzystania (bloki nazwane)
Bloki obsługują wszystkie instrukcje DML, a także
DDL
[DECLARE ]
deklaracje zmiennych, wyjątki
BEGIN
wyrażenia SQL i PL/SQL
[EXCEPTION ]
obsługa wyjątków
END;
[] – opcjonalnie
Blok nie może być pusty.
Sekcja deklaracji
7
Sekcja wykonawcza
8
Jest to sekcja opcjonalna
Umieszczamy w niej zmienne i ich typy, stałe, kursory,
wyjątki definiowane przez użytkownika, wszystko to
do czego odwołujemy się w kolejnej sekcji bloku
Możliwość dokonania inicjalizacji
Przykład
DECLARE
v_zmienna NUMBER;
Obowiązkowa
Rozpoczyna się od słowa kluczowego BEGIN
Musi posiadać co najmniej jedną instrukcję
Może zawierać dowolną liczbę bloków PL/SQL,
zagnieżdżonych
Może zawierać polecenia SQL lub PL/SQL
Sekcja wyjątków
9
Typy bloków
10
Bloki anonimowe
Opcjonalna
Rozpoczyna się od słowa kluczowego EXCEPTION
Pozwala na przechwytywanie błędów, które
wystąpiły w sekcji wykonawczej
Bloki nazwane
Funkcje
Procedury
Bloki anonimowe
11
Przykład
12
Nie posiadają nazwy i nie są przechowywane w
bazie danych
Można w nich wywoływać inne programy, ale ich
nigdzie nie można wywołać
Są kompilowane za każdym razem gdy program
jest uruchamiany
Struktura bloku anonimowego – jak wcześniej.
SET SERVEROUTPUT ON; - na zewnątrz bloku anonimowego umożliwia
wypisywanie komunikatów
DBMS_OUTPUT.PUT_LINE (‘komunikat’); - wypisywanie komunikatu
DBMS_OUTPUT.NEW_LINE; - przejście do nowej linii
Uruchamianie bloku
13
Uruchamianie bloku
14
Oracle SQL Developer: Uruchamianie: Run Script (F5); Wyniki: Script Output
Oracle SQL*Plus: Uruchamianie: znak „/” na końcu kodu
Uruchamianie bloku
15
Podstawowe składowe języka
16
Identyfikatory
Ograniczniki
Literały
Słowa zarezerwowane
Komentarze
Oracle SQL*Plus: Jeżeli kod bloku jest zapisany w pliku (ze znakiem „/” na końcu):
Uruchamianie: start ścieżka dostępu do pliku
@ ścieżka dostępu do pliku
Identyfikatory
17
Ograniczniki
18
Służą do nazywania zmiennych, kursorów, funkcji, procedur,
etc.,
Zasady tworzenia identyfikatorów:
+,-,*,/ - operatory matematyczne
>,<,<>,=,!= - operatory porównania
--, /*, */ - komentarze
<<, >> - etykiety
% - atrybuty (TYPE, etc.)
’ – ogranicznik łańcuchów znaków
” – ogranicznik identyfikatorów
:= - przypisanie, inicjalizacja zmiennej
|| - łączenie łańcuchów znaków
<30 znaków
Rozpoczynają się literą
Mogą zawierać znaki $,#,_ i cyfry (oprócz pierwszej pozycji),
Nie mogą zawierać znaków przestankowych, odstępów i myślników,
Nie mogą zawierać słów zarezerwowanych,
Wyjątek to identyfikatory w cudzysłowach - można w nich
stosować prawie wszystko.
Literały
19
Deklaracja zmiennych i stałych
20
Wartości, które nie są reprezentowane przez
identyfikatory, ani nie są wyliczane na podstawie
innych wartości:
Zmienne:
identyfikator typ_danych [NOT NULL] [:=wart_pocz | DEFAULT wart_pocz];
Stałe:
identyfikator CONSTANT typ_danych [:=wart_pocz | DEFAULT wart_pocz];
Znakowe: np. ’abc’
Liczbowe: 1, 2, 456
Logiczne: TRUE, FALSE
Związane z datą ’23-12-2013’
DECLARE
v_zmienna NUMBER(5);
v_nr NUMBER(3) NOT NULL := 10;
c_stala CONSTANT NUMBER(2) DEFAULT 13;
v_sprawdz BOOLEAN NOT NULL := TRUE;
Typy zmiennych
21
Typy znakowe
22
Typy skalarne – typ o pojedynczej wartości
CHAR ([(max długość)] – domyślnie 1; typ danych o
stałej długości, pojemność określamy w bajtach:
maksymalnie 32 767 bajtów w PL/SQL (w SQL –
2000 bajtów)
VARCHAR2 (max długość) - typ danych o zmiennej
długości, maksymalnie 32 767 bajtów ( w SQL –
4000 bajtów)
Znaki i łańcuchy znaków
Liczby
Typy logiczne
Data i czas
Typy złożone – typ złożony z kilku odrębnych wartości (np.
rekord, kolekcja (tablice, listy) , instancja typu obiektowego)
Wskaźniki – logiczny wskaźnik danej wartości lub kursora
LOB – identyfikator typu wielkoobiektowego (ang. large
object)
Typy liczbowe i logiczne
23
Data i czas
24
NUMBER [(precyzja, skala)] – precyzja: wartości od 1 do 38,
skala: -84 do 127, identyczny z typem NUMBER bazy danych
Podtypy: REAL (63 cyfry), DOUBLE PRECISION (126 cyfr), FLOAT (126
cyfr)
BINARY_DOUBLE, BINARY_FLOAT - od wersji Oracle 10g,
typ zmiennoprzecinkowy o podwójnej (pojedynczej) precyzji
PLS_INTEGER – zakres od -2 147 483 648 do 2 147 483
647. Potrzebuje mniej przestrzeni na dysku niż NUMBER;
bardziej efektywne wyliczenia
BOOLEAN – wartości TRUE, FALSE, NULL
DATE – podstawowy typ daty i czasu; przechowuje
rok, miesiąc, dzień, godzinę, minutę, sekundę
TIMESTAMP [(precyzja)] – rozszerzenie typu DATE o
ułamki sekund, w tym celu określa się precyzję 0-9,
domyślnie 6
Przechowywanie okresów czasów:
INTERVAL YEAR [(precyzja)] TO MONTH – w latach i
miesiącach
INTERVAL DAY [(precyzja_dni)] TO SECOND
[(precyzja_ułamki_sekund)] – w dniach, minutach i
sekundach
Typy zakotwiczone
25
Instrukcje warunkowa
26
zmienna%TYPE
tabela.kolumna%TYPE
tabela%ROWTYPE
IF warunek THEN
instrukcja-1;
END IF;
v_imie VARCHAR2(15);
v_moje_imie v_imie%TYPE;
ksiazki_record t_ksiazka%ROWTYPE
IF warunek-1 THEN
instrukcja-1;
ELSIF warunek-2 THEN
instrukcja-2;
ELSE
instrukcja-3;
END IF;
Instrukcja warunkowa
Instrukcja CASE
v_cena t_ksiazka.cena%TYPE;
27
IF warunek THEN
instrukcja-1;
ELSE
instrukcja-2;
END IF;
28
……...
IF v_cena > 100 THEN
RETURN (v_cena*1.1);
ELSIF v_cena >= 50 THEN
RETURN (v_cena*1.2);
ELSE
RETURN (v_cena*1.25);
END IF;
……….
Od wersji 9i,
Alternatywa dla instrukcji warunkowych IF
upraszczająca składnię
CASE warunek
WHEN kryterium1 THEN operacje1;
WHEN kryterium2 THEN operacje2;
…
[ELSE operacje;]
END CASE;
Instrukcja CASE - przykład
29
CASE z wyszukiwaniem
30
DECLARE
CASE [TRUE| FALSE]
WHEN warunek1 THEN operacje1;
WHEN warunek2 THEN operacje2;
…
[ELSE operacje;]
END CASE;
selector NUMBER := 0;
BEGIN
CASE selector
WHEN 0 THEN
dbms_output.put_line('Case 0!');
WHEN 1 THEN
dbms_output.put_line('Case 1!');
ELSE
dbms_output.put_line('No match!');
Domyślnie poszukuje warunku prawdziwego (TRUE)
END CASE;
END;
/
CASE z wyszukiwaniem - przykład
31
Pętla prosta
32
BEGIN
CASE
LOOP
instrukcje;
EXIT [WHEN warunek];
END LOOP;
WHEN 1 = 2 THEN
dbms_output.put_line('Case [1 = 2]');
WHEN 2 = 2 THEN
dbms_output.put_line('Case [2 = 2]');
ELSE
dbms_output.put_line('No match');
END CASE;
END;
/
Wynik działania CASE
Przykład
33
CONTINUE [WHEN]
34
DECLARE
Od wersji 11g
Dodatkowe sterowanie pętlą
Działanie: natychmiast kończy aktualną iterację i
przechodzi do pierwszego działania w pętli
counter NUMBER;
first BOOLEAN;
BEGIN
LOOP
IF NVL(counter,1) >= 1 THEN
IF NOT NVL(first,TRUE) THEN
counter := counter + 1;
ELSE
counter := 1;
first := FALSE;
END IF;
END IF;
dbms_output.put_line('Iteration ['||counter||']');
EXIT WHEN NOT counter < 3;
END LOOP;
END;
/
CONTINUE
35
CONTINUE
36
DECLARE
counter NUMBER;
IF counter = 2 THEN CONTINUE;
first BOOLEAN;
ELSE dbms_output.put_line('Index ['||counter||'].');
BEGIN
LOOP
IF NVL(counter,1) >= 1 THEN
IF NOT NVL(first,TRUE) THEN
counter := counter + 1;
ELSE
counter := 1;
first := FALSE;
END IF;
END IF;
EXIT WHEN NOT counter < 3;
IF counter = 2 THEN CONTINUE;
ELSE dbms_output.put_line('Index ['||counter||'].');
END IF;
END LOOP;
END;
CONTINUE WHEN counter = 2;
dbms_output.put_line('Index ['||counter||'].');
Instrukcje FOR i WHILE
37
Instrukcja FOR - przykład
38
DECLARE
v_licznik NUMBER(1) :=0;
v_ostatni NUMBER(1);
v_min NUMBER(1) := 1;
v_max NUMBER(1) := 5;
WHILE warunek LOOP
instrukcje;
END LOOP;
FOR licznik IN [REVERSE] min..max LOOP
instrukcje;
END LOOP;
BEGIN
Nie trzeba deklarować zmiennej i
FOR i IN v_min..v_max LOOP
v_licznik := v_licznik + 1;
v_ostatni := i;
END LOOP;
dbms_output.put_line(‘Ostatni indeks:’
|| TO_CHAR(v_ostatni) || ‘. Liczba petli:’
|| TO_CHAR(v_licznik));
END;
Instrukcja NULL
Polecenie SELECT INTO
39
40
DECLARE
i NUMBER(2) :=0;
BEGIN
………
IF i > 10 THEN
dbms_output.put_line(‘i jest większe od 10’);
ELSE
NULL;
END IF;
END;
/
NULL – oznacza brak akcji
SELECT lista_zmiennych
INTO nazwa_zmiennej | nazwa_rekordu
FROM tabela
[ WHERE warunki];
SELECT INTO przekazuje wartości uzyskane z bazy
(lista_zmiennych) do zmiennych występujących w
klauzuli INTO
Polenie musi zwrócić jeden wiersz
SELECT INTO - przykład
41
Pojęcie kursora
42
DECLARE
bonus
Udostępnia dane zwrócone przez zapytanie
Otwarcie kursora to pobranie części bieżących
danych, co oznacza, że modyfikacje danych po
jego otwarciu nie będą widoczne w zbiorze, który
zwrócił kursor.
Dwa typy kursorów
NUMBER(8,2);
BEGIN
SELECT salary * 0.10 INTO bonus
FROM employees
WHERE employee_id = 100;
DBMS_OUTPUT.PUT_LINE('bonus = ' ||
TO_CHAR(bonus));
Niejawne
Jawne
END;
/
Typy kursorów
Atrybuty kursora SQL
43
44
Niejawne
Deklarowane są dla
wszystkich instrukcji DML
oraz SELECT
PL/SQL zarządza
automatycznie kursorem
niejawnym
Parametry kursora:
SQL%nazwa_parametru
Jawne
Deklarowane przez
programistę
Programista zarządza
kursorem jawnym
Parametry kursora:
Nazwa_kursora%nazwa_p
arametru
Nazwa atrybuty
Opis
SQL%ROWCOUNT
Liczba wierszy, których dotyczyła ostatnia instrukcja SQL
SQL%FOUND
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
Kursory niejawne - przykład
45
Kursory niejawne - przykład
46
DECLARE
DECLARE
v_usuniete VARCHAR2(30);
n NUMBER;
BEGIN
BEGIN
DELETE
FROM t_z_ksiazka
WHERE id_zamowienia = &par;
SELECT 1 INTO n FROM dual;
dbms_output.put_line('Selected ['||SQL%ROWCOUNT||']');
END;
====================================================================
BEGIN
v_usuniete := TO_CHAR(SQL%ROWCOUNT)|| ‘rekordow
usunietych.’;
END;
UPDATE system_user
SET last_update_date = SYSDATE;
IF SQL%FOUND THEN
dbms_output.put_line('Updated ['||SQL%ROWCOUNT||']');
ELSE
dbms_output.put_line('Nothing updated!');
END IF;
END;
Kursory jawne
47
Sterowanie kursorami jawnymi
48
CURSOR nazwa_kursora [(parametr [, parametr] … )] IS instrukcja_select;
NIE
parametr ::= nazwa_parametru typ danych [{:= | DEFAULT wyrażenie}]
DECLARE
CURSOR kursor (p_isbn VARCHAR(10)) IS
SELECT *
FROM t_ksiazka
WHERE isbn = p_isbn;
OPEN
FETCH
PUSTY?
TAK
CLOSE
Kursory jawne
49
Atrybuty kursora jawnego
50
Nazwa atrybuty
Opis
%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
DECLARE ….. ;
OPEN nazwa_kursora [(parametr [, parametr] ...)];
FETCH nazwa_kursora INTO zmienna [ , zmienna ...];
CLOSE nazwa_kursora;
Kursor jawny - przykład
51
Pętla kursorowa FOR
52
DECLARE
CURSOR k_cursor IS SELECT * FROM t_z_ksiazka
WHERE isbn = 1;
k_record t_z_ksiazka%ROWTYPE;
v_ilosc t_z_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;
FOR nazwa_rekordu IN nazwa_kursora LOOP
instrukcja-1;
instrukcja-2;
…….
END LOOP;
Niejawne instrukcje OPEN, FETCH, CLOSE
zmienna nazwa_rekordu – zadeklarowana niejawnie
Pętla kursorowa FOR - przykład
53
Pętla kursorowa FOR- przykład
54
DECLARE
CURSOR k_cursor
(p_zam t_zamowienie.id_zamowienia%TYPE) IS
SELECT *
FROM t_z_ksiazka
WHERE id_zamowienia = p_zam;
DECLARE
CURSOR a_cursor IS SELECT * FROM t_autor;
======== Metoda 1 ========================
BEGIN
FOR i IN a_cursor LOOP
dbms_output.put_line(i.nazwisko);
END LOOP;
END;
======== Metoda 2 ========================
BEGIN
FOR i IN (SELECT * FROM t_autor) LOOP
dbms_output.put_line(i.nazwisko);
END LOOP;
END;
BEGIN
FOR i IN k_cursor(1) LOOP
dbms_output.put_line(i.isbn);
END LOOP;
END;
Klauzula FOR UPDATE
55
Klauzula WHERE CURRENT OF
56
CURSOR nazwa_kursora [(parametr,… )]
IS instrukcja_select
[FOR UPDATE [OF (lista_kolumn) [NOWAIT]];
Służy do blokowania rekordów po otwarciu kursora
Rekordy są dostępne dla innych sesji, ale tylko w trybie
do odczytu
Gdy użyjemy NOWAIT, przy otwieraniu kursora
program zostanie zamknięty, jeśli nie może utworzyć
blokady na wyłączność.
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;
Klauzula WHERE CURRENT OF
57
Literatura
58
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
McLaughlin, Michael, Oracle Database 11g PL/SQL
programming, Oracle Press, 2008
www.oracle.com