Cursor Explícito ou Implícito ? Qual o melhor ?
Olá pessoal !
Se você tem alguma dúvida sobre usar cursor explícito ou implicíto, hoje eu apresentarei 1 motivo para usar sempre o implícito. Não utilizarei nenhum argumento do tipo ‘código mais limpo’ ou ‘performance com BULK’. Apenas a abertura e fechamento de cursores !
No cursor explícito, a abertura e fechamento de cursores deve ser controlada. O problema é que muitos desenvolvedores acabam não codificando bem a parte lógica, esquecendo um pouco das exceções. Veja o exemplo abaixo:
DECLARE
vNUM NUMBER;
CURSOR c1 IS
SELECT * FROM dual;
r1 c1%ROWTYPE;
BEGIN
OPEN c1;
LOOP
FETCH c1 INTO r1;
-- Forçando exceção
vNUM := 'X';
EXIT WHEN c1%NOTFOUND;
END LOOP;
CLOSE c1;
EXCEPTION
WHEN OTHERS THEN
IF c1%ISOPEN THEN
DBMS_OUTPUT.PUT_LINE('Cursor Aberto !');
ELSE
DBMS_OUTPUT.PUT_LINE('Cursor Fechado !');
END IF;
END;
Resultado
----------------------
1 Cursor Aberto !
Veja que o cursor ficou aberto ao estourar exceção. Isso se resolve facilmente, alterando o código na exception e fechando o cursor.
EXCEPTION
WHEN OTHERS THEN
IF c1%ISOPEN THEN
DBMS_OUTPUT.PUT_LINE('Cursor Aberto !');
CLOSE c1;
IF NOT c1%ISOPEN THEN
DBMS_OUTPUT.PUT_LINE('Cursor Fechado !');
END IF;
ELSE
DBMS_OUTPUT.PUT_LINE('Cursor Fechado !');
END IF;
END;
Resultado
----------------------
1 Cursor Aberto !
2 Cursor Fechado !
Executemos o mesmo script, mas utilizando cursor implícito:
DECLARE
vNUM NUMBER;
CURSOR c1 IS
SELECT * FROM dual;
r1 c1%ROWTYPE;
BEGIN
FOR r1 IN c1
LOOP
-- Forçar Exception
vNUM := 'X';
END LOOP;
EXCEPTION
WHEN OTHERS THEN
IF c1%ISOPEN THEN
DBMS_OUTPUT.PUT_LINE('Cursor Aberto !');
ELSE
DBMS_OUTPUT.PUT_LINE('Cursor Fechado !');
END IF;
END;
Resultado
----------------------
1 Cursor Fechado !
Não entrarei no mérito de que cursores são fechados automaticamente, após o término de um bloco anônimo. Pense no contexto de uso dentro de Packages e procedures, onde é necessário o fechamento dos cursores ao se utilizar um cursor explicíto.
Perceba que utilizando FOR o cursor é automáticamente fechado, após o estouro da exceção ! Essa é uma vantagem na utilização de cursores implicítos !
Sobre qual é o melhor ? Tire suas próprias conclusões com as informações acima ! 😛
Bom pessoal, espero que essa informação ajude !
Um grande abraço
Qual seria a vantagem de um cursor explicito ao inves de um implicito?
Opa, eae Denis !
Então, tudo depende de uma análise de caso a caso. Porém, vou te dar uma resposta em um contexto amplo.
Eu enxergo 2 casos pelo menos:
1) No cursor explicíto você pode varrre mais de uma vez o conjunto de dados. Pois ele só será fechado quando você o fizer;
2) Reutilização do cursor em diversas partes diferente do código.
Como eu disse, o ideal é avaliar caso a caso. Mas posso afirmar que em alguns desses casos, os pontos que citei acima são realmente uma baita vantagem.