Documente online.
Zona de administrare documente. Fisierele tale
Am uitat parola x Creaza cont nou
 HomeExploreaza
upload
Upload




Cursoare - Ce sunt cursoarele?

Oracle


Cursoare

Ce sunt cursoarele?

Cursoarele sunt structuri care permit utilizatorului sa denumeasca o zona privata de memorie care urmeaza sa pastreze o anumita instructiune, īn vederea utilizarii ei ulterioare īn sistemul Oracle exista doua tipuri de cursoare: implicite si explicite. Limbajul PL/sQL declara īn mod implicit un cursor pentru fiecare dintre instructiunile DML insert, delete si update. Cursoarele explicite sunt declarate de utilizator si sunt folosite pentru 15115p1517p procesarea rezultatelor interogarii lor, care returneaza linii multiple.



Numarul de linii returnate de o interogare poate fi zero, una sau mai multe, īn functie de conditiile de cautare ale interogarii. In Oracle, cursoarele sunt destinate procesarii linie cu linie a seturilor de rezultate multi-linie. īn lipsa cursoarelor, proiectantul de aplicatii Oracle ar trebui sa preia si sa gestioneze īn mod explicit fiecare linie selectata de interogare.

Liniile multiple returnate de o interogare se numesc setul activ. Limbajul PL/SQL defineste dimensiunea acestuia ca reprezentānd numarul de linii care au īndeplinit criteriile de cautare si au format setul activ. Figura 17.1 ilustreaza un cursor care contine linii multiple. Prin definitie, fiecare cursor poseda un indicator care tine evidenta liniei curent accesate, ceea ce permite programului dumneavoastra sa proceseze liniile, una cāte una.

Figura 17

Cursor multi-linie.

De ce se folosesc cursoarele?

Puteti sa va imaginati un cursor ca fiind un fisier care urmeaza sa fie procesat de la īnceput pāna la sfārsit, īnregistrare cu īnregistrare. Cursoarele sunt folosite pentru 15115p1517p a procesa linie cu linie seturi de rezultate multi-linie. īn plus, cursoarele tin evidenta liniei curent accesate, ceea ce permite procesarea interactiva a setului activ.

Utilizarea mai multor cursoare simultan poate īmbunatati performantele sistemului prin reducerea frecventei interpretarii si deschiderii cursoarelor. Dupa fiecare parcurgere iterativa a cursorului, acesta pastreaza suficiente informatii despre setul activ si instructiunile SQL īncāt poate fi re-executat de mai multe ori. Fiecare noua iteratie este realizata fara sa fie necesara redeschiderea si interpretarea cursorului.

Prin deschiderea mai multor cursoare, forma interpretata a instructiunilor SQL poate fi salvata, elimin ndu-se īn acest fel neajunsurile legate de deschiderea si interpretarea repetata a cursorului.

Cum se folosesc cursoarele

Limbajul SQL*Plus creeaza īn mod implicit un cursor pentru fiecare instructiune DML executata. Acest lucru survine indiferent daca interogarea returneaza una sau mai multe linii. Utilizatorii au posibilitatea sa declare īn mod explicit un cursor pentru procesarea linie cu linie a setului multi-linie activ īn continuare, sunt prezentate etapele care trebuie parcurse pentru crearea si utilizarea cursoarelor:

Declararea cursorului

Deschiderea cursorului

Preluarea datelor īn cursor

Īnchiderea cursorului

Declararea cursoarelor explicite

Cursorul trebuie declarat īnainte de a se face referire la el īn instructiuni PL/SQL. Prin declararea unui cursor se realizeaza urmatoarele:

Se denumeste cursorul

Se asociaza o interogare cursorului

Numele pe care īl atribuiti unui cursor nu este o variabila PL/SQL ci un identificator nedeclarat. Numele este folosit pentru a face referire la interogare. Nu puteti sa atribuiti valori numelui unui cursor si nici sa- folositiJn expresii. Rezultatele interogarii cursorului devin setul activ al cursorului īn exemplul urmator, este declarat un cursor numit c_articole:

declare

cursor c_articole IS

select * from lista_articole;

Nu exista o limita predefinita īn legatura cu numarul maxim de cursoare care pot exista pe parcursul unei sesiuni. Singura limitare a numarului de cursoare este data de memoria disponibila pentru gestionarea lor. De asemenea, exista o limita a numarului de cursoare din īntregul sistem per sesiune. Aceasta limita este data de valoarea parametrului open_cursor si este stabilita de administratorul bazei de date.

Atunci cānd lucrati cu cursoare, puteti folosi parametri pentru a transfera cursorului diverse Valori care sa le īnlocuiasca pe cele prestabilite. Acesti parametri trebuie declarati odata cu cursorul. Parametrii pot sa apara īntr-o interogare oriunde poate sa apara o constanta. Exemplul urmator ilustreaza cursorul c_articole si parametrul v_ cant_articol:

declare

cursor c_articole (v_ cant_articol NUMBER) IS select from lista_articole where cant_articol > v_cant_articol;

Deschiderea cursoarelor explicite

Deschiderea cursoarelor explicite duce la executarea interogarii si la identificarea setului activ. Setul activ contine toate liniile care īndeplinesc criteriile de cautare. Pentru cursoarele care sunt declarate folosind clauza for update, programul Oracle blocheaza liniile care īndeplinesc criteriile de cautare ale interogarii cursorului.

īn instructiunea cursor open trebuie specificate valorile actuale pentru fiecare parametru specificat īn declaratia cursorului. In caz contrar, parametrii care apar īn declaratia cursorului vor avea valorile prestabilite.

īntr-o instructiune open, puteti asocia parametrii actuali, parametrilor formali ai unui cursor folosind notatia pozitionala. Instructiunea urmatoare deschide cursorul c_articole:

open c_articole

Atunci cānd este executata comanda open, cursorul identifica numai acele linii care satisfac interogarea. Practic, liniile nu sunt citite pāna cānd nu se face preluarea cursorului. Cursorul este initializat la prima linie a setului activ.

Atributele cursoarelor explicite

Fiecare cursor pe care īl definiti are patru atribute. Prin accesarea acestor atribute pot fi obtinute informatii utile despre cursor. Cele patru atribute ale cursoarelor sunt urmatoarele:

% is open

Acest atribut boolean are valoarea True īn cazul īn care cursorul este deja deschis. Exemplul urmator verifica daca cursorul numit c_cursor este deschis. Daca este deja deschis, este executata instructiunea fetch. Daca este īnchis, este executata comanda de deschidere a cursorului.

Begin

if c_cursor%isopen then

fetch c_cursor into v_cant_comanda,

v_pret_comanda;

else

open c_cursor;

end if;

end;

%not found

Acest atribut boolean are valoarea True īn cazul īn care nu a fost returnata nici o linie la cea mai recenta executare a instructiunii fetch. īntrucāt instructiunea fetch va esua mai devreme sau mai tārziu fara sa fie generata nici o exceptie, acest atribut este folosit pentru a parasi ciclul atunci cānd nu mai este nici o linie de procesat, ca īn exemplul urmator:

loop

fetch c_cursor into v_cant_comanda,

v_pret_comanda;

exit when c_cursor%not found;

end loop;

end;

found

Acest atribut are valoarea True pāna īn momentul īn care ultima instructiune fetch nu preia nici o linie. Acest atribut este opusul logic al atributului not found. Dupa deschiderea cursorului si īnaintea primei preluari cu instructiunea fetch, atributul % found are valoarea Nuli. Dupa prima preluare, acest atribut va avea valoarea True pāna īn momentul īn care comanda fetch nu mai returneaza nici o linie. Acest exemplu foloseste atributul % found pentru a controla executia comenzii insert

begin

loop

fetch c_cursor into v_cant_comanda,

v_pret_comanda;

i c_cursor%found then

insert into lista_comenzi values

(v_cant_comanda, v_pret_comanda);

else

exit;

end if;

end loop;

end;

% rowcount

Acest atribut numeric este egal cu numarul total de linii returnate de instructiunea f etch. Dupa deschiderea cursorului si īnaintea primei preluari cu instructiunea f etch, acest atribut are valoarea zero. Dupa prima executare a instructiunii f etch, el are valoare numarului total de linii preluate pāna īn acel moment. Exemplul urmator foloseste atributul & r owcount pentru a opri executia dupa procesarea primelor 100 de linii:

begin

loop

fetch c_cursor into v_cant_comanda,

v_pret_comanda ;

exit when c__cursor%rowcount > 100;

end loop;

end;

Utilizarea cursoarelor explicite

Comanda fetch preia liniile din setul activ una cāte una. Prima instructiune fetch sorteaza setul activ, daca este necesar. Cursorul avanseaza la linia urmatoare a setului activ ori de cāte ori este executata o comanda fetch. Singura cale de a parcurge setul activ este prin intermediul comenzii fetch. Pentru fiecare valoare a unei coloane returnata de interogarea cursorului, īn lista trebuie sa existe o variabila care sa-i corespunda. Exemplul urmator ilustreaza utilizarea comenzilor open si f etch, precum si a atributului &notfound:

begin

open c_vizitatori

loop

fetch c_vizitatori into lista vizitatori

exit whe"n c_vizitatori%notfound

end loop;

end;

Īn exemplul precedent, setul activ definit de cursorul c_vizitatori este procesat linie cu linie. Ciclul iterativ de citire si procesare a liniilor individuale continua pāna la procesarea tuturor liniilor din setul activ.

Exemplul urmator este un script PL/SQL complet care utilizeaza un cursor pentru procesarea datelor īn mod individual īn acest exemplu, vor fi citite īnregistrari continānd date referitoare la vānzari īnregistrararile sunt procesate, iar datele sunt inserate īn fisierul lista_comenzi.

Daca vreti sa consultati o linie preluata anterior, trebuie sa īnchideti si sa redeschideti cursorul, dupa care sa preluati liniile, una cāte una. Daca vreti sa schimbati setul activ, trebuie sa atribuiti noi valori variabilelor de intrare din interogarea cursorului si sa redeschideti cursorul. In acest fel, este re-creat setul activ continānd rezultatele actualizate ale interogarii.

declare

v_cant_comanda number(7,2):=0;

v_pret_comanda number(7,2):=0;

total_cx>manda number(11,2):=0;

cursor c_comenzi is - declaratia cursorului

select cant, pret from lista_comenzi;

begin

open c_comenzi     deschiderea cursorului

loop

fetch c_comenzi into v_cant_comanda, v_pret_comanda;

exit when c_comenzi%notfound;

- calculeaza totalul comandat pe baza valorilor cursorului dupa care insereaza rezultatul īn tabelul s_comenzi

v_total_comanda = v_pret_comanda * v_cant_comanda; insert Tnto s_comenzi values (v_total_comanda); end loop;

close c_comenzi; - inchide cursorul

commit;    - salveaza rezultatele prelucrarii

end; - programul se incheie

Īnchiderea cursoarelor explicite

Pentru a īnchide un cursor, trebuie sa executati instructiunea close. Instructiunea urmatoare īnchide cursorul c_comenzi:

close c_comenzi;

Atunci cānd programul utilizatorului īncheie legatura cu serverul, acesta īnchide īn mod implicit cursorul.

Cursoare implicite

Oracle creeaza si deschide īn mod implicit un cursor pentru fiecare instructiune SQL care nu face parte dintr-un cursor declarat īn mod explicit. Cel mai recent cursor implicit poate fi considerat a fi cursorul SQL. Comenzile open, close si fetch nu pot fi folosite īn legatura cu cursoarele implicite īn schimb, puteti folosi atributele cursoarelor pentru a obtine prin intermediul cursorului SQL informatii despre cea mai recent executata instructiune SQL.

Atributele cursoarelor implicite

La fel ca si cursoarele explicite, cursoarele implicite au patru atribute: %isopen, %f ound, rowcount si %notf ound. Puteti folosi aceste atribute īn instructiuni procedurale, īnsa nu si īn instructiuni SQL. Aceste atribute, prezentate īn lista care urmeaza, va permit sa accesati informatii īn legatura cu cea mai recenta executie a uneia dintre comenzile insert, select into, update si delete.

%isopen

Īntr-un cursor implicit, acest atribut are īntotdeauna valoarea False. Programul īnchide automat cursoarele implicite dupa executarea instructiunilor SQL asociate.

notfound

Acest atribut boolean are valoarea True īn cazul īn care nu a fost returnata nici o linie de catre instructiunea select into sau daca o instructiune insert, update sau delete nu a afectat nici o linie.

%found

Pāna īn momentul executarii unei instructiuni SQL de manipulare a datelor, acest atribut are valoarea Nuli. Daca o instructiune insert, update sau delete afecteaza una sau mai multe linii, acesta ia valoarea True. īn caz contrar, atributul % f ound ia valoarea False.

%rowcount

Acest atribut returneaza numarul de linii afectate de o instructiune insert, update sau delete sau numarul de linii returnate de o instructiune select into. Atributul % rowcount returneaza zero daca instructiunea SQL nu afecteaza sau nu returneaza nici o linie.

Valoarea atributelor cursorului se refera īntotdeauna la cea mai recent executata instructiune SQL. Acest lucru este valabil indiferent unde apare instructiunea īn program.

Cursoare de pachet

Sistemul Oracle permite stocarea specificatiei cursorului īntr un pachet (package). īn aceasta specificatie, trebuie folosita clauza return. Aceasta abordare a cursoarelor va permite sa modificati corpul cursorului fara sa schimbati specificatia acestuia. Exemplul urmator ilustreaza un cursor de pachet numit clsal_ang:

create package ang_lunar as

cursor c_sal_ang return ang%rowtype;

end ang_lunar;

create package body ang_lunar as

cursor c_sal_ang return ang%rowtype;

select marca_ang, salariu__ang from lista_ang where

data_angajaFe > '01-JAN-1986'; END ang_lunar;

Īn specificatia cursorului nu apare instructiune select deoarece clauza return defineste tipul de data al valorii rezultante. In exemplul precedent, este folosit atributul %rowtype īn clauza return pentru a furniza tipul de īnregistrare care reprezinta o linie a bazei de date.

Īn corpul cursorului apare o instructiune select si aceeasi clauza return ca si īn specificatia cursorului.

Utilizarea ciclurilor for īn interiorul cursoarelor

Ca scurtatura pentru preluarea liniilor īntr-un cursor, puteti folosi ciclul for. Ciclul for este parcurs iterativ o data pentru fiecare linie returnata de interogare. Cursorul īnsusi este cel care determina momentul īn care se paraseste ciclul for. Ciclul for simplifica codificarea prin efectuarea urmatoarelor operatii:

La initierea ciclului, este executata īn mod implicit o instructiune open

La fiecare parcurgere a ciclului este executata īn mod implicit o instructiune fetch

La parasirea ciclului este executata īn mod implicit o instructiune close

Urmatorul exemplu PL/SQL utilizeaza ciclul for pentru a acumula comenzile pentru fiecare linie de produse:

accept comanda_prod prompt 'Introduceti numarul comenzii:'

declare

v_id_comanda s_articol_comanda%tip := p_comanda;

v_total_comanda number (11,2) :=0;

cursor c_cursor is    - declaratie cursor

select cod_art, pret, cant from lista_articole

where cod_comanda = v_id_comanda;

begin    - deschidere implicita

for inreg_comanda in c_cursor loop - preluare implicita

v_total_comanda := v_total_comanda +

((inreg_comanda.cant * inreg_comanda.cant)*.95) ;

insert into lista__comenzi (cod_articol, total_comanda)

values (inreg_comanda.cod_articol, v__total_comanda);

end loop;    - īnchidere implicita

commit;    - finalizarea tranzactiei

end;

Aliasurile cursoarelor

Cāmpurile unui cursor implicit au aceleasi nume ca si cāmpurile corespunzatoare din instructiunea interogativa. Din aceasta cauza'apar probleme atunci cānd instructiunea interogativa contine o expresie. De exemplu, cum veti face referire la numele coloanei īn urmatoarea interogare?

cursor is c_vanzari

select nr_agent_vanzari, (total_vanzari/12)*.015 from

lista_vanzari

Īn situatiile de acest gen, folositi un alias pentru a face referire la articolul (total vanzari *. 015 al listei select īn exemplul urmator, este folosit acelasi cursor ca si īn exemplul anterior, īnsa este declarat aliasul comision_vanzari

cursor is c_vanzari

select nr_agent_vanzari, (total_vanzari/12)*.015

comision_vanzari

from lista^vanzari

Din acest moment, puteti face pur si simplu referire la aliasul comision_vanzari

if comision_vanzari > 5000 then ...

Performantele cursoarelor

Viteza de executie a apelurilor din interiorul cursoarelor poate fi īmbunatatita prin ajustarea parametrului cursor_space_for time. Acest parametru precizeaza momentul īn care o zona SQL partajata poate dealocata pentru a face loc unei noi instructiuni SQL. Valoarea prestabilita a acestui parametru este False. Acest lucru īnseamna ca Oracle poate dealoca o zona SQL partajata din biblioteca cache chiar daca este deschis un cursor al unei aplicatii asociat cu instructiunile acesteia. Valoarea True īnseamna ca o zona SQL partajata poate fi dealocata numai atunci cānd toate cursoarele aplicatiei asociate instructiunilor SQL ale acesteia sunt īnchise.

Daca valoarea acestui parametru este False, programul Oracle trebuie sa consume timp si resurse pentru a verifica daca zona SQL partajata care contine instructiunea SQL se gaseste īn biblioteca cache. Stabilirea parametrului la valoarea True face ca serverul' sa realizeze o mica economie de timp si poate īmbunatati performantele apelurilor de executie. Aceasta deoarece programul Oracle nil trebuie sa verifice zona SQL partajata care nu poate fi dealocata atāt timp cāt un cursor al unei aplicatii este asociat cu ea.

Rezumat

Cursoarele sunt structuri PL/SQL care va permit sa procesati linie cu linie rezultatele unei interogari multi-linie. Cursoarele implicite sunt create pentru fiecare instructiune DML, īn timp ce cursoarele explicite sunt create de utilizatori pentru procesarea interogarilor care returneaza linii multiple.

Cursoarele permit utilizatorului sa proceseze linie cu linie rezultatele unei interogari multi-linie. De asemenea, cursoarele īmbunatatesc procesarea codului prin eliminarea interpretarii repetate a acestuia. Mai mult, pentru executarea instructiunilor unui cursor trebuie sa īl deschideti o singura data, īmbunatatindu-se astfel performantele serverului.

Īn acest capitol, au fost trecute īn revista cele patru etape necesare pentru utilizarea corecta a cursoarelor. Acestea sunt: declararea cursorului, deschiderea cursorului, preluarea datelor si īnchiderea cursorului.

De asemenea, ati aflat care este diferenta dintre cursoarele implicite si cele explicite si ati vazut cāteva aplicatii practice ale ambelor.


Document Info


Accesari: 5867
Apreciat: hand-up

Comenteaza documentul:

Nu esti inregistrat
Trebuie sa fii utilizator inregistrat pentru a putea comenta


Creaza cont nou

A fost util?

Daca documentul a fost util si crezi ca merita
sa adaugi un link catre el la tine in site


in pagina web a site-ului tau.




eCoduri.com - coduri postale, contabile, CAEN sau bancare

Politica de confidentialitate | Termenii si conditii de utilizare




Copyright © Contact (SCRIGROUP Int. 2024 )