Współczesne bazy danych posiadają cechy zarówno relacyjne jak i obiektowe. Do tej pory poznaliśmy cechy relacyjne, teraz czas na poznanie cech obiektowych.
Rozważymy dwa rodzaje obiektów, które można przechowywać w obiektowo-relacyjnej bazie danych:
Od dwudziestu już lat trwają prace nad nowymi koncepcjami w bazach danych polegającymi na dołączaniu cech obiektowych do istniejących relacyjnych baz danych. Otrzymano w ten sposób model obiektowo-relacyjny i faktycznie na takim modelu jest w tej chwili oparty nowy Standard języka SQL:1999.
Przypomnimy najpierw ogólne znaczenie typów obiektowych. Realizują one zasadę abstrakcji w dwóch postaciach:
Oto podsumowanie zalet użycia obu rodzajów abstrakcji w bazach danych:
Rys. 7.1 Struktura obiektu
Osobno specyfikujemy publiczny interfejs obiektów składający się z deklaracji atrybutów i specyfikacji metod oraz prywatną implementację obiektów składającą się z definicji (ciał) metod.
Rys. 7.2 Struktura typu obiektowego
Oto składnia specyfikacji typu obiektowego (w wersji podstawowej):
CREATE TYPE nazwa_typu AS OBJECT (atrybut typ_danych, ... MEMBER sygnatura procedury lub funkcji [, klauzula PRAGMA], ... ); |
Oto składnia implementacji typu obiektowego (w wersji podstawowej):
CREATE TYPE BODY nazwa_typu AS MEMBER implementacja procedury lub funkcji; ... END; |
Przykład
Zdefiniujemy dwa typy obiektowe: typ nazwisk Name_typ
oraz typ pracowników
Emp_typ
:
CREATE TYPE Name_typ
AS OBJECT(
F_name VARCHAR2(25),
L_name VARCHAR2(25),
Initials VARCHAR2(7),
MEMBER FUNCTION Full_name RETURN VARCHAR2,
PRAGMA RESTRICT_REFERENCES(Full_name, WNDS, RNDS, WNPS, RNPS ));
/
CREATE TYPE BODY Name_typ AS
MEMBER FUNCTION Full_name RETURN VARCHAR2 IS
BEGIN
RETURN (L_name || ' ' || F_name );
END Full_name;
END;
/
CREATE TYPE Emp_typ
AS OBJECT(
Emp_id NUMBER(7),
Name
Name_typ, -- typ obiektowy
Street VARCHAR2(25),
City VARCHAR2(15),
State CHAR(2),
Zip INTEGER,
MEMBER FUNCTION Get_name RETURN VARCHAR2,
PRAGMA RESTRICT_REFERENCES(Get_name, WNDS, RNDS, WNPS, RNPS),
MEMBER PROCEDURE Set_l_name (v_name VARCHAR2));
/
CREATE TYPE BODY Emp_typ AS
MEMBER FUNCTION Get_name RETURN VARCHAR2 IS
BEGIN
RETURN (Name.L_name ||' '|| Name.F_name);
END;
MEMBER PROCEDURE Set_l_name (v_name VARCHAR2) IS
BEGIN
Name.L_name := v_name;
END;
END;
/
Metody to funkcje lub procedury, które tworzymy w definicji
typu obiektowego w celu zaimplementowania zachowania się obiektów danego typu.
Aplikacja wywołuje metody aby uzyskać w efekcie to zachowanie. Są trzy typy
metod: metody składowe obiektów (metody typu MEMBER
),
metody konstruktorów obiektów (metody typu CONSTRUCTOR
) oraz metody statyczne, czyli odnoszące się do całego
typu (metody typu STATIC
). W tym wykładzie rozważamy tylko metody składowe
obiektów oraz metody konstruktora obiektów implementowane przez system – oprócz
tego są jeszcze metody konstruktorów definiowane przez użytkowników.
Między typami obiektowymi obowiązuje dziedziczenie tak jak w językach
programowania - realizowane przez operator UNDER
. Na przykład:
CREATE TYPE Person
AS OBJECT (
First VARCHAR2(50),
Last VARCHAR2(50)) NOT FINAL;
/
CREATE TYPE Emp
UNDER Person (
Salary NUMBER) FINAL;
/
Obiekt typu Emp ma wszystkie cechy obiektu typu Person a poza tym jeszcze cechy wprowadzone w specyfikacji typu Emp.
DECLARE
x Emp:=Emp('Jan','Kowalski',10000);
BEGIN
DBMS_OUTPUT.Put_line(x.first||' '||x.last||' '||x.salary);
END;
/
Wymagana jest specyfikacja NOT FINAL
dla typów obiektowych,
które mogą być wzorcami dla podtypów podlegając dalszemu dziedziczeniu
czyli nie są one końcowe w hierarchii dziedziczenia. Domyślną specyfikacją jest
FINAL
- typ obiektowy nie podlega dalszemu dziedziczeniu.
Tak jak w językach programowania jest możliwość zastosowania przesłaniania metod.
CREATE TYPE Figure
AS OBJECT (
NOT INSTANTIABLE MEMBER FUNCTION area RETURN NUMBER
) NOT INSTANTIABLE NOT FINAL;
/
CREATE TYPE Rect
UNDER Figure
(x NUMBER,
y NUMBER,
OVERRIDING MEMBER FUNCTION area RETURN NUMBER) FINAL;
/
CREATE TYPE BODY Rect AS
OVERRIDING MEMBER FUNCTION area RETURN NUMBER IS
BEGIN
RETURN x*y;
END;
END;
/
Definicja metody area w podtypie Rect przesłania jej specyfikację
w nadtypie Figure. Wymagane jest słowo kluczowe OVERRIDING
. Domyślną specyfikacją
metody jest NON OVERRIDING.
Słowo kluczowe NON INSTANTIABLE
dla
typu obiektowego oznacza, że nie można tworzyć instancji danego typu
obiektowego a dla metody - brak implementacji. Domyślną specyfikacją w
obu przypadkach jest INSTANTIABLE
.
Informacje o typach obiektowych znajdują się w perspektywie słownika danych o nazwie:
Informacje o metodach typów obiektowych znajdują się odpowiednio w perspektywach słownika danych:
DROP TYPE typ;
|
Zdefiniowanego typu obiektowego można używać do
tworzenia tabel obiektowych tego typu.
CREATE TABLE nazwa_tabeli OF nazwa_typu [(więzy spójności)]; |
Zauważmy, że więzów spójności nie określa się w definicji typu obiektowego, tylko w definicji samej tabeli.
W utworzonej tabeli obiektowej są
zapisywane obiekty typu obiektowego na tej samej zasadzie co wiersze tabeli
relacyjnej. To znaczy, wartości atrybutów tworzą wiersz, na którym działają
metody określone w danym typie obiektowym.
CREATE TABLE Name_table OF Name_typ; -- tabela obiektowa
INSERT INTO Name_table
VALUES('Jan','Kowalski','JK');
INSERT INTO Name_table
VALUES('Anna','Kowalska','AK');
SELECT nt.F_name, nt.Full_name()
FROM Name_table nt;
Dla każdego typu obiektowego automatycznie jest tworzona metoda konstruktora obiektu tego typu. Ma ona taką samą nazwę jak typ obiektowy oraz ma argumenty takich typów jak atrybuty typu obiektowego. Rozważmy typ obiektowy:
CREATE TYPE Tv_type
AS OBJECT (
Tv_category VARCHAR2(20),
Screen_size NUMBER(4));
/
Oto przykłady użycia jego konstruktora w bloku PL/SQL:
DECLARE
v_new_tv tv_type := Tv_type('WEB tv', 32);
v_alt_tv Tv_type;
BEGIN
v_alt_tv := Tv_type('Big Screen', 72);
END;
/
oraz w instrukcji INSERT do tabeli obiektowej:
CREATE TABLE Tv OF Tv_type;
INSERT INTO Tv VALUES(Tv_type('Color tv', '28'));
Wynikiem instrukcji:
SELECT *
FROM Name_table p
WHERE p.L_name LIKE 'K%';
jest zbiór wierszy:
F_NAME L_NAME INITIAL -------------- ------------- ------- Jan Kowalski JK Anna Kowalska AK
Wynikiem instrukcji:
SELECT VALUE(p) AS Osoba
FROM Name_table p
WHERE p.L_name LIKE 'K%';
jest zbiór obiektów reprezentowanych przy użyciu konstruktora typu obiektowego (VALUE(p) - oznacza obiekt wskazywany przez p):
OSOBA(F_NAME, L_NAME, INITIALS) ----------------------------------- NAME_TYP('Jan', 'Kowalski', 'JK') NAME_TYP('Anna', 'Kowalska', 'AK')
Wstawiamy albo bezpośrednio tak jak do tabeli relacyjnej:
INSERT INTO Name_table
VALUES('Jan','Kowalski','JK');
albo z użyciem konstruktora:
INSERT INTO Name_table
VALUES(Name_typ('Jan','Kowalski','JK'));
Modyfikujemy albo bezpośrednio, tak jak w tabeli relacyjnej:
UPDATE Name_table p
SET p.L_name = 'Janusz'
WHERE p.L_name = 'Jan';
albo z użyciem konstruktora:
UPDATE Name_table p
SET p = Name_typ('Janusz','Kowalski','JK')
WHERE p.L_name = 'Jan';
Obiekty z tabeli obiektowej usuwamy tak jak wiersze z tabeli relacyjnej:
DELETE FROM Name_table p
WHERE p.L_name = 'Janusz';
Oprócz nowego rodzaju tabel obiektowych możemy także używać tabel relacyjnych z kolumnami typów obiektowych. Wartościami wpisywanymi do kolumn tabeli mogą więc być instancje typów obiektowych. Na przykład:
CREATE TABLE Emp1( -- tabela relacyjna
Empno NUMBER PRIMARY KEY,
Name Name_typ, -- kolumna typu
obiektowego
Sal NUMBER,
Kier REFERENCES Emp1);
Dla każdego typu obiektowego Type jest automatycznie
definiowany jego typ referencyjny oznaczany przez REF Type. Typu tego można używać
jako typu atrybutów obiektów bądź kolumn w tabeli relacyjnej. Daje to możliwość
wiązania wartości atrybutu bądź wartości w kolumnie z innym obiektem
podobnie jak klucz obcy odwołuje się do klucza głównego. Jest to
alternatywny sposób tworzenia powiązań.
CREATE TYPE Dept_Type
AS OBJECT(
Name VARCHAR2(10),
Loc VARCHAR2(50));
CREATE TYPE Emp_Type
AS OBJECT(
Name VARCHAR2(20),
Sal NUMBER,
Dept_ref REF Dept_Type);
CREATE TABLE Obj_Dept OF Dept_Type;
CREATE TABLE Obj_Emp OF Emp_Type -- tabela obiektowa
(Dept_ref SCOPE IS Obj_Dept);
CREATE TABLE Rel_emp( -- tabela relacyjna
Id NUMBER PRIMARY KEY,
Name VARCHAR2(20),
Sal Number,
Dept_ref REF Dept_Type SCOPE IS Obj_Dept);
Ze względu na możliwość istnienia wielu tabel obiektowych tego samego typu, definiując typ referencyjny trzeba wskazać do obiektów której tabeli odwołuje się on. Służy do tego klauzula SCOPE IS – proszę zwrócić uwagę na jej użycie w powyższych przykładach.
W instrukcjach SQL można bezpośrednio nawigować przez referencje w taki
sam sposób jak to ma miejsce dla obiektów. Gdybyśmy chcieli dla każdego pracownika wypisać
nazwę jego departamentu, użylibyśmy następującej instrukcji SELECT:
SELECT e.Name, e.Dept_ref.Name
FROM Obj_emp e;
Dla tabeli relacyjnej instrukcja SELECT jest taka sama.
SELECT e.Name, e.Dept_ref.Name
FROM Rel_emp e;
Natomiast w kodzie PL/SQL nawigacja przez referencje jest niedozwolona i wymaga
użycia specjalnej funkcji SQL:
DEREF(p) -
obiekt na który wskazuje referencja p
|
Jest też funkcja odwrotna:
REF(o) -
referencja do obiektu o identyfikatorze o
|
Reasumując, w obiektowo-relacyjnej bazie danych pojawiają się dwa nowe rodzaje wartości związane z zapisem danych na dysku: referencje do obiektów oraz jednoznaczne identyfikatory obiektów. Każda implementacja obiektowo-relacyjnej bazy danych może używać innych zbiorów tych wartości, co powoduje, że obiektowo-relacyjna baza danych przestaje być przenaszalna (jako zbiór tabel z atomowymi, skalarnymi wartościami) między różnymi systemami. Tracimy więc wielką zaletę relacyjnych baz danych.
Atrybut typu obiektowego lub kolumna tabeli nie koniecznie musi być typu prostego ale może być typu zbiorowego (kolekcji). Są dwa rodzaje kolekcji:
Oto przykład zastosowania typu VARRAY. Najpierw definicja typu obiektowego o nazwie Projekt.
CREATE TYPE Projekt AS OBJECT ( Num_proj NUMBER(3), Tytuł VARCHAR2(35), Koszt NUMBER(7,2));Teraz zdefiniujemy typ kolekcji o nazwie Lista – mianowicie tablicę VARRAY projektów. Jako argument VARRAY podajemy górne ograniczenie liczby projektów - w naszym przykładzie będzie to liczba 3.
CREATE TYPE Lista AS VARRAY(3) OF Projekt;Oto definicja tabeli, w której jeden z atrybutów o nazwie Projekty jest typu tablicowego Lista.
CREATE TABLE Wydziały (
Id_wydz NUMBER(2),
Nazwa VARCHAR2(15),
Budżet NUMBER(11,2),
Projekty Lista);
Do inicjacji wartości kolekcji służy funkcja konstruktora o tej samej nazwie co typ kolekcji. A więc do tabeli
Wydziały wstawiamy wartości atrybutów kolekcji w następujący sposób – należy
tylko pamiętać aby zgodnie ze specyfikacją tablica
Projekty nie miała więcej niż trzy elementy (ale może mieć mniej).
INSERT INTO Wydziały VALUES(1,'Informatyka',100000, Lista(Projekt(1,'Analiza',123), Projekt(2,'Projekt',456)));Również w takiej postaci system wypisuje wartości kolekcji przy wykonywaniu instrukcji SELECT. Wynik instrukcji
SELECT w.Nazwa, w.Projekty FROM Wydziały w;jest wypisywany w postaci:
NAZWA PROJEKTY(NUM_PROJ, TYTUŁ, KOSZT) ----------- -------------------------------------------------------- Informatyka LISTA(PROJEKT(1,'Analiza',123),PROJEKT(2,'Projekt',456))Natomiast tylko w kodzie PL/SQL do poszczególnych elementów kolekcji można dostawać się używając naturalnej dla tablic składni:
Nazwa_kolekcji(wskaźnik)
|
Przykład
Przy reprezentowaniu departamentów i pracowników za pomocą
dwóch tabel obiektowych Obj_Dept i Obj_Emp odpowiednio typów Dept_Type i
Emp_Type, łatwo jest wyznaczyć dla pracownika jego departament (poprzez
atrybut Dept_ref
). Natomiast wobec braku klucza obcego i indeksu na nim, trudno
wyznaczyć dla danego departamentu wszystkich pracowników zatrudnionych w tym
departamencie. Rozwiązaniem tego problemu jest zastosowanie kolekcji.
Definiujemy typ kolekcji
CREATE TYPE Pracownicy AS VARRAY(100) OF REF Emp_Type;
i do typu Dept_Type dodajemy atrybut Kadra
typu tej kolekcji.
Oto pełne rozwiązanie.
CREATE TYPE Dept_Type
AS OBJECT(
Name VARCHAR2(10),
Loc VARCHAR2(50),
Kadra Pracownicy);
-- pracownicy w departamencie
/
CREATE TYPE Emp_Type
AS OBJECT(
Name VARCHAR2(20),
Sal NUMBER,
Dept_ref REF Dept_Type); --
departament
pracownika
/
CREATE TABLE Obj_Dept OF Dept_Type;
CREATE TABLE Obj_Emp OF Emp_Type
(Dept_ref SCOPE IS Obj_Dept);
Przykład
Zaprezentujemy przetwarzanie wartości w kolekcji przy użyciu kodu PL/SQL. Wypiszemy
wydziały razem z projektami realizowanymi w tych wydziałach. Użyjemy
metody Count zdefiniowanej dla kolekcji. Wartością Nazwa_kolekcji.Count
jest liczba elementów w kolekcji. Metoda ta pozwala przejrzeć wszystkie
elementy kolekcji.
CREATE OR REPLACE PROCEDURE Wypisz AS
lis Lista;
BEGIN
FOR z IN (SELECT * FROM Wydzialy) LOOP
DBMS_OUTPUT.Put_line('Projekty Wydzialu: '||z.Nazwa);
lis:=z.Projekty;
FOR i IN 1..lis.Count LOOP
DBMS_OUTPUT.Put_line(lis(i).Num_proj||' '||lis(i).Tytul);
END LOOP;
END LOOP;
END;
Realizacja polecenia:
Exec Wypisz
spowoduje wyświetlenie (należy pamiętać o włączeniu opcji SET SERVEROUTPUT ON
):
Projekty Wydzialu: Informatyka
1 Analiza
2 Projekt
Język SQL i jego rozszerzenie PL/SQL w dotychczas omawianej postaci umożliwiają dostęp do standardowych typów danych zapisanych w bazie danych i umożliwiają wykonywanie na nich operacji. Są jednak sytuacje, gdy może się to okazać niewystarczające.
Z taką sytuacją mamy do czynienia w przypadku danych, których format wykracza poza format standardowych typów danych. Przykładem takich danych są duże obiekty, jak rysunki (grafika), fotografie, zdjęcia satelitarne i rentgenowskie (zdjęcia binarne), video, animacje, wywiady (audio/video), muzyka, odgłosy dźwiękowe (sound waveforms), skrypty, dokumenty tekstowe, książki. Wprowadzono więc, zarówno do Standardu SQL:1999, jak i do
Oracle nowe typy danych dla dużych obiektów tzw. LOB (ang. large
objects). Oprócz samych dużych obiektów wspomnimy również krótko o narzędziach do operowania na nich
dostarczonych w standardowym pakiecie Oracle o nazwie
DBMS_LOB
.
W Oracle są cztery rodzaje dużych obiektów LOB:
|
Rys. 7.3 Rodzaje dużych obiektów
Duże obiekty są przechowywane albo wewnętrznie - wewnątrz bazy
danych
– dotyczy to wartości typów CLOB
, NCLOB
, BLOB
, albo zewnętrznie w plikach systemu operacyjnego – dotyczy to wartości typu
BFILE
, które są dostępne z serwera Oracle tylko w trybie odczytu. Serwer Oracle nie potrafi
automatycznie dokonywać konwersji danych między różnymi typami danych, np. z wartości typu
CLOB
do wartości typu BLOB
.
Z każdym dużym obiektem LOB jest związana:
Zasada jest taka, że w kolumnie typu LOB jest zapisywany lokalizator
LOB – nie cała jego zawartość. Interfejsy programistyczne operujące wartościami
LOB używają tych lokalizatorów w podobny sposób, jak używa się uchwytów do plików w systemie
operacyjnym.
Przypisując lokalizator do nowej zmiennej lub nowego wiersza następuje skopiowanie wartości dużego obiektu i wygenerowanie nowego
lokalizatora. W przypadku zewnętrznych wartości
LOB nie są one kopiowane (a więc wskaźnik do tego samego pliku
BFILE
może występować w różnych wierszach w tabeli).
Poniższy rysunek ilustruje fakt, że wartością atrybutu, kolumny lub zmiennej jest lokalizator (wskaźnik) do dużego obiektu LOB, który jest zapisany albo w samej bazie danych albo poza nią (w przypadku wartości BFILE).
Rys. 7.4 Reprezentacja dużego obiektu
Przykład
Rozważmy tabelę pracowników, której kolumny są
typów LOB. Dla każdego pracownika zamieszczamy jego życiorys
(Resume
), zdjęcie (Picture
) oraz film video (Video
).
CREATE TABLE Employee(
Empno NUMBER,
Ename VARCHAR2(35),
Resume CLOB,
Picture BLOB,
Video BFILE);
Zewnętrzne obiekty LOB nie są zapisywane w bazie danych lecz każdy w osobnym pliku systemu operacyjnego.
W systemie Oracle został wprowadzony nowy rodzaj obiektu bazodanowego o nazwie katalog związany z typem danych
BFILE
. Mianowicie,
katalog jest to obiekt bazodanowy reprezentujący katalog systemu operacyjnego.
Służy do administrowania dostępem do obiektów bazy danych typu
BFILE
przechowywanych w plikach poza bazą danych. Fizyczny katalog jest tworzony pod systemem operacyjnym z uprawnieniami odczytu dla procesów Oracle. Pliki
w tym katalogu nie mogą być
ani zmieniane ani usuwane przez system Oracle.
Na przykład, instrukcja:
CREATE DIRECTORY Videos AS '/oracle/lob/';
tworzy obiekt bazodanowy reprezentujący katalog /oracle/lob
Rys. 7.5 Obiekt bazy danych typu katalog
Zilustrujemy użycie obiektów LOB w instrukcjach SQL na kilku przykładach.
INSERT INTO Employee VALUES
(7897,'Jan Kowalski','Znakomity aktor', NULL, NULL);
INSERT INTO Employee VALUES
(7898,'Piotr Jankowski', Empty_CLOB(), Empty_BLOB(), Bfilename('VIDEOS','J.IMG'));
UPDATE Employee e
SET e.Resume =(SELECT f.Resume FROM Employee1 f
WHERE f.Ename='Kowalski')
WHERE e.Empno = 4508;
W powyższym przykładzie NULL
oznacza brak lokalizatora obiektu LOB,
Empty_BLOB()
i Empty_CLOB()
oznaczają lokalizator do pustego obiektu.
Stałe tekstowe zostają automatycznie przekształcone do typu CLOB. Natomiast,
funkcja
Bfilename('VIDEOS','J.IMG'))
zwraca lokalizator dużego obiektu
przechowywanego w pliku
J.IMG
.
Na zawartościach obiektów BLOB
i
CLOB
można operować za pomocą procedur i funkcji specjalnego pakietu DBMS_LOB w podobny
sposób jak to się robi na zawartościach plików binarnych.
DECLARE
lobloc CLOB; -- lokalizator LOB
text VARCHAR2(2000);
amount NUMBER;
offset INTEGER;
BEGIN
text := 'tekst do wpisania do LOB';
SELECT e.Resume INTO lobloc
FROM Employee e WHERE e.Empno = 5887
FOR UPDATE; -- konieczna blokada wiersza
offset := DBMS_LOB.Getlength(lobloc) + 1;
amount := Length(text);
DBMS_LOB.Write(lobloc, amount, offset, text);
COMMIT;
DBMS_OUTPUT.Put_line('Wpisano ' || To_char(amount) ||' znaków');
END;
/
W szczególności, procedura DBMS_LOB.Write(lobloc,
amount, offset, text)
dopisuje
do istniejącej zawartości obiektu o lokalizatorze lobloc zawartość text o długości
amount począwszy od miejsca offset. Oto jej sygnatura:
PROCEDURE Write( Lobdst IN OUT BLOB|CLOB, -- dwie możliwości Amount IN OUT BINARY_INTEGER, Offset IN INTEGER := 1, Buffer IN RAW|VARCHAR2) -- RAW dla BLOB, VARCHAR2 dla CLOB
Jak widać, nie jest przewidziana możliwość wpisywania danych do obiektu typu BFILE
!
Oto sygnatura funkcji Read odczytującej określoną przez amount ilość danych dużego
obiektu BLOB
, CLOB
lub BFILE
od jego pozycji
offset i zapisującą je do bufora buffer:
PROCEDURE Read( Lobsrc IN BFILE|BLOB|CLOB , -- trzy możliwości! Amount IN OUT BINARY_INTEGER, Offset IN INTEGER, Buffer OUT RAW|VARCHAR2) -- RAW dla BLOB i BFILE, VARCHAR2 dla CLOBJest też możliwość załadowania zawartości obiektu
BFILE
(czyli pliku binarnego) do bazy danych w postaci obiektu
BLOB
lub CLOB
. Służy do tego procedura Loadfromfile o następującej sygnaturze:
PROCEDURE Loadfromfile( Lobdst IN OUT BLOB|CLOB, Src_file IN BFILE, Amount IN INTEGER, Dest_offset IN INTEGER := 1, Src_offset IN INTEGER := 1)
Oto przykład użycia procedury Loadfromfile do wstawienia zdjęcia osoby
dostępnego jako obiekt typu BFILE - do tabeli Emp w postaci obiektu wewnętrznego
typu
BLOB
:
CREATE TABLE Emp( Empno INTEGER(5); Ename VARCHAR2(50); Zdjecie BLOB); DECLARE b BLOB; f BFILE; BEGIN INSERT INTO Emp VALUES(1, 'Kowalski', Empty_BLOB()); SELECT Zdjecie INTO b FROM Emp WHERE Empno=1 FOR UPDATE; f:=Bfilename('KATALOG','Kowalski.gif'); DBMS_LOB.Loadfromfile(b,f,DBMS_LOB.Lobmaxsize); END; /
Nie ma bezpośredniej operacji usuwania obiektu LOB. W celu usunięcia go, można albo usunąć cały wiersz z obiektem, albo zastąpić go w wierszu innym. Najpierw, usunięcie wiersza z obiektem LOB:
DELETE FROM Employee e
WHERE e.Ename = 'Jan Kowalski';
Z kolei, usunięcie obiektu LOB w wierszu:
UPDATE Employee e SET e.Resume = Empty_CLOB()
WHERE e.Ename = 'Jan Kowalski';
Zapoznaliśmy się ze sposobem przechowywania w bazie danych i posługiwania się w języku SQL:
Wykład stanowi tylko wprowadzenie do pełnego opanowania przez czytelnika posługiwania się obiektami. Zachęcamy czytelnika do wykonania podanych poniżej zadań domowych oraz przestudiowania dokumentacji Oracle: Application Developer's Guide - Object-Relational Features i Application Developer's Guide - Large Objects (LOBs).
Rodzi się naturalne pytanie. Czy lepiej konstruować relacyjne czy relacyjno-obiektowe bazy danych?
Skoro więc trapią nas wątpliwości,
który rodzaj baz danych wybrać, może wybierzemy trzeci rodzaj baz danych, które
właśnie na naszych oczach powstają – tzw. bazy XMLowe. Wprowadzenie do nich jest
tematem osobnego wykładu.
typ obiektowy - definiowany przez użytkownika typ danych, który hermetyzuje strukturę danych łącznie z metodami potrzebnymi do operowania na strukturze danych. Można stosować dziedziczenie własności między typami obiektowymi i ich przesłanianie (powtórne zdefiniowanie w podtypie).
tabela obiektowa - tabela, w której są zapisywane obiekty typu obiektowego na tej samej zasadzie co wiersze tabeli relacyjnej. To znaczy, wartości atrybutów tworzą wiersz, na którym działają metody określone w typie obiektowym.
typ referencyjny - typ wartości reprezentujący odwołania do obiektów w bazie danych. Jest obiektową alternatywą do wiązania tabel przez wartość klucza obcego.
kolekcja - typ wartości w bazie danych reprezentujący zbiory wartości prostych lub obiektów.
duży obiekt LOB - typ wartości w bazie danych reprezentujący duże obiekty w rodzaju dokumentów tekstowych, plików z obrazem, dźwiękiem lub video.DBMS_LOB - pakiet z operacjami na dużych obiektach LOB.
CLOB
;CLOB
;CLOB
na ekran.