Oracle PL/SQL 강좌
명시적 커서(EXPLICIT CURSOR) 15 23 99,999+

by 구루비 명시적 커서 EXPLICIT CURSOR OPEN FETCH CLOSE PL/SQL CURSOR [2002.01.20]


커서란 무엇인가?

  • - 커서는 Private SQL의 작업 영역이다.
  • - 오라클 서버에 의해 실행되는 모든 SQL문은 연관된 각각의 커서를 소유하고 있다.
  • - 커서의 종류
    • 암시적 커서 : 모든 DML과 PL/SQL SELECT문에 대해 선언된다.
    • 명시적 커서 : 프로그래머에 의해 선언되며 이름이 있는 커서이다.

Explicit Cursor의 흐름도?

문법(Syntax)

커서 열기(OPEN)

  • - 커서의 열기는 OPEN문을 사용한다.
  • - 커서안의 검색이 실행되며 아무런 데이터행을 추출하지 못해도 에러가 발생하지 않는다.
  • - 문법 : OPEN cursor_name;

커서 패치(FETCH)

  • - 커서의 FETCH는 현재 데이터 행을 OUTPUT변수에 반환 한다.
  • - 커서의 SELECT문의 컬럼의 수와 OUTPUT변수의 수가 동일해야 한다.
  • - 커서 컬럼의 변수의 타입과 OUTPUT변수의 데이터 타입도 동일해야 한다.
  • - 커서는 한 라인씩 데이터를 패치 한다.
  • - 문법 : FETCH cursor_name INTO variable1, variable2;

커서 닫기(CLOSE)

  • - 사용을 맞친 커서는 반드시 닫아 주어야 한다.
  • - 필요하다면 커서를 다시 열 수 있다.
  • - 커서를 닫은 상태에서 FETCH를 할 수 없다.
  • - 문법 : CLOSE cursor_name;

Explicit Cursor 예제

 
-- 특정 부서의 평균급여와 사원수를 출력..
SQL> CREATE OR REPLACE PROCEDURE ExpCursor_Test 
       (v_deptno IN  dept.deptno%TYPE)
       
     IS

       CURSOR dept_avg IS
       SELECT b.dname, COUNT(a.empno) cnt, 
               ROUND(AVG(a.sal),3) salary
       FROM emp a, dept b
       WHERE a.deptno = b.deptno
         AND b.deptno = v_deptno
       GROUP BY b.dname ;

       -- 커서를 패치하기 위한 편수 선언
       v_dname   dept.dname%TYPE;
       emp_cnt   NUMBER;
       sal_avg   NUMBER;

     BEGIN

       -- 커서의 오픈
       OPEN dept_avg;

       -- 커서의 패치 
       FETCH dept_avg INTO v_dname, emp_cnt, sal_avg;
  
       DBMS_OUTPUT.PUT_LINE('부서명 : ' || v_dname);
       DBMS_OUTPUT.PUT_LINE('사원수 : ' || emp_cnt);
       DBMS_OUTPUT.PUT_LINE('평균급여 : ' || sal_avg);

       -- 커서의 CLOSE
       CLOSE dept_avg;      

    EXCEPTION
      WHEN OTHERS THEN
        DBMS_OUTPUT.PUT_LINE(SQLERRM||'에러 발생 ');

   END;
   /

-- DBMS_OUTPUT.PUT_LINE을 출력하기 위해 사용
SQL> SET SERVEROUTPUT ON ;

SQL> EXECUTE ExpCursor_Test(30);
부서명 : SALES
사원수 : 6
평균급여 : 1550.833
    

- 강좌 URL : http://www.gurubee.net/lecture/1064

- 구루비 강좌는 개인의 학습용으로만 사용 할 수 있으며, 다른 웹 페이지에 게재할 경우에는 출처를 꼭 밝혀 주시면 고맙겠습니다.~^^

- 구루비 강좌는 서비스 제공을 위한 목적이나, 학원 홍보, 수익을 얻기 위한 용도로 사용 할 수 없습니다.

by 장룡일 [2005.12.21 11:23:51]
고맙습니다.

by 까만아이 [2006.04.03 16:23:04]
정말 간결하고도 쉽게 파악할 수 있는 유익한 강좌네요 ㅋ
막 회사생활 하면서... Oracle잘 몰라서 덜덜되고 있는데...
많은 도움이 되네여 ^^
앞으로도 좋은 강좌 많이 부탁드리겠습니다.
수고하세요 (__)

by 하얀아이 [2006.10.08 13:24:34]
정말로 감사합니다.

by 김남열 [2006.11.20 11:34:16]
열공하고 있습니다. 감사^^

by 난봉 [2007.02.06 17:38:10]
WHEN OTHERS THEN는 어떤 예외경우인가요?
커서를 통해서 OPEN->FETCH->CLOSE하는데 이것을 못하는 그런 경우인가요?

by 오타발견 [2007.03.14 10:56:26]
-- 커서를 패치하기 위한 편수 선언
v_dname dept.dname%TYPE;
emp_cnt NUMBER;
sal_avg NUMBER;
------------------------------------------------------
변수 선언

by My1over [2007.03.22 10:30:20]
SELECT b.dname, COUNT(a.empno) cnt, ROUND(AVG(a.sal),3) salary
INTO v_dname, emp_cnt, sal_avg
FROM emp a, dept b
WHERE a.deptno = b.deptno
AND b.deptno = v_deptno
GROUP BY b.dname ;

이라고 해도 같은 결과가 나올텐데요
커서를 사용하는 이유와 어떠한 경우에 커서를 사용해야 하는지 궁금합니다 ^^

by 12 [2007.05.25 14:15:03]
근데 커서를 왜써요?ㅠ

by 홍성원 [2007.07.11 15:42:12]
대단이 이해가 쉽게 간결하게 ... 대단한 강좌..

by 디스타임 [2007.11.09 10:35:01]
이거 출력이 되는지요? 글구 궁금해서 그러는데
패치 변수 선언한 것들 (v_dname,emp_cnt,sal_avg)을 어딘가에 매치시켜야 되지 않나요? 가령, v_danme이 사원수라는걸 어떻게 알수있나요?
아시는분 답변좀 부탁드립니다. ^^
그런데 답변이 언제쯤 올까요? ^^;

by 디스타임 [2007.11.09 10:47:42]
다시 해보니 실행은 되네요.^^

by 디스타임 [2007.11.09 10:49:16]
위의 내용을 다시 읽어보니 패치 설명할때 나오네요 --

by 김윤경 [2007.11.09 11:23:44]
테스트 하며 학습하니 이해가 잘 되네요;

by 창아 [2007.11.22 16:42:25]
커서는 언제 사용되나요??그리고 사용하는 이유는 뭔가요?

by 배기완 [2008.02.13 18:09:12]
데이터가 단일행일 경우엔 INTO문으로 해결이 되지만 데이터가 복수행일 경우 FETCH문을 써서 한행씩 데이터를 읽어 처리할수 있습니다.

by T_R [2008.06.04 16:37:34]
CURSOR 는 저장이 돼는 곳이 아니고 단지 어떠한 행을 지시하는 하나의 지휘봉의 역할을 하는 것입니다.

뽑고자 하는 데이타의 위치를 지정 해 주는 거라고 보시면 ?틉? 하구요....

보통 패키지 선언 할때 OUT 값을 지시 해주는거 같더라구요....

잘은 모르지만 어떠한 값을 가지고 있는건 아닌거 같아요

by 맘부자 [2008.11.17 17:48:57]
최근 3년동안 프로시져를 사용해보지를 않아서 다 까먹었는데. 강좌보면서 조금씩 살아나고 있습니다. 강의가 훌륭합니다.

by 나그네 [2009.05.12 17:37:43]
만약에 커서의 데이터가 1이상이 나올 경우네는
루프 형식으로 돌게 되어있는건가요?

by 마농 [2009.05.12 17:45:34]
-- 반복문과 함께 돌리셔야 합니다.
OPEN dept_avg;
LOOP
FETCH dept_avg INTO v_dname, emp_cnt, sal_avg;
EXIT WHEN dept_avg%NOTFOUND;
...
END LOOP;
CLOSE dept_avg;

by 신입개발자 [2014.10.16 20:01:28]

여기서는 DECLARE를 선언하지 않나요>??


by 망고네 [2015.05.21 13:32:07]

커서의 사용 이유가 검색해보니  이렇게 나오네요.

 오라클에서 CURSOR란 시스템 글로벌 영역의 공유 풀 내에 저장공간을 사용하여 사용자가 SQL 문을 실행시키면 결과값을 저장공간에 가지고 있다가 원하는 시기에 순차적으로 fetch해 처리하여 해당 결과 셋을 프로그래밍적으로 접근할수 있게 도와주는 기능이다.


by 박환규 [2016.06.28 16:22:24]

질문이 있습니다. 

커서라는게 다중의 값을 지정한 위치에서 꺼내오는 걸로 이해 했는데 그럼 table에서 값을 저장해 뽑아 보는 거와 무슨 차이가 있는 겁니까?


by 라프 [2020.05.15 14:24:28]

감사합니다.^^

댓글등록
SQL문을 포맷에 맞게(깔끔하게) 등록하려면 code() 버튼을 클릭하여 작성 하시면 됩니다.
로그인 사용자만 댓글을 작성 할 수 있습니다. 로그인, 회원가입