The difference among Cursor, hidden Cursor, and dynamic Ref Cursor is displayed in PLSQL. plsqlref
1. Explicit cursor
Explicit is relative to implicit cursor, that is, there is a clear declared cursor. The declaration of an explicit cursor is similar to the following (for detailed syntax, refer to plsql ref doc ):
Cursor cursor_name (parameter list) is select...
The cursor from declare, open, fetch, close is a complete life journey. Of course, such a cursor can be used for multiple open operations. The explicit cursor is a static cursor, and its scope is global, but it must be understood that, static cursor can be used only by pl/SQL code. The following is an example of a simple static explicit cursor:
Declare
Cursor get_gsmno_cur (p_nettype in varchar2) is
Select gsmno
From gsm_resource
Where nettype = p_nettype and status = '0 ';
V_gsmno gsm_resource.gsmno % type;
Begin
Open get_gsmno_cur ('20140901 ');
Loop
Fetch get_gsmno_cur into v_gsmno;
Exit when get_gsmno_cur % notfound;
Dbms_output.put_line (v_gsmno );
End loop;
Close emp_cur;
Open get_gsmno_cur ('20140901 ');
Loop
Fetch get_gsmno_cur into v_gsmno;
Exit when get_gsmno_cur % notfound;
Dbms_output.put_line (v_gsmno );
End loop;
Close get_gsmno_cur;
End;
/
The above anonymous block is used to implement the number selection function. We explicitly define a get_gsmno_cur, and then output the available mobile phone numbers corresponding to the short number in the current system according to different number segments. Of course, there is no such use in practical applications. I just want to use an explicit cursor usage.
Ii. Implicit cursor
Implicit cursor is of course relative to explicit, that is, there is no clear declare of cursor. In Oracle's PL/SQL, all DML operations are parsed into an implicit cursor named SQL in Oracle, which is transparent to us.
In addition, the pointer for loop in some loop operations we mentioned above are all implicit cursor.
Implicit cursor Example 1:
Create table zrp (str VARCHAR2 (10 ));
Insert into zrp values ('abcdefg ');
Insert into zrp values ('abcxefg ');
Insert into zrp values ('abcyefg ');
Insert into zrp values ('abcdefg ');
Insert into zrp values ('abczefg ');
COMMIT;
SQL> begin
2 update zrp SET str = 'updated' where str like '% D % ';
3 ifSQL % ROWCOUNT = 0 then
4 insert into zrp values ('20140901 ');
5 end if;
6 end;
7/
PL/SQL procedure successfully completed
SQL> select * from zrp;
STR
----------
UpdateD
ABCXEFG
ABCYEFG
UpdateD
ABCZEFG
SQL>
SQL> begin
2 update zrp SET str = 'updated' where str like '% S % ';
3 ifSQL % ROWCOUNT = 0 THEN
4 insert into zrp values ('20140901 ');
5 end if;
6 end;
7/
PL/SQL procedure successfully completed
SQL> select * from zrp;
STR
----------
UpdateD
ABCXEFG
ABCYEFG
UpdateD
ABCZEFG
0000000
6 rows selected
SQL>
Implicit cursor Example 2:
Begin
For rec in (select gsmno, status from gsm_resource) loop
Dbms_output.put_line (rec. gsmno | '--' | rec. status );
End loop;
End;
/
Iii. REFcursor
Ref cursor is a dynamic cursor (this query is not known until running ).
Technically, static cursor and ref cursor at the most basic level are the same. A typical PL/SQL cursor is static by definition. The Ref cursor is the opposite. It can be opened dynamically or with a set of SQL static statements, the method is determined by logic (one IF/THEN/ELSE code block opens one or other queries ). For example, the following code block shows a typical static SQL cursor, cursor C. In addition, it shows how to open a query by using dynamic or static SQL with the ref cursor (L_CURSOR in this example:
Declare
Type rc is ref cursor;
Cursor c is select * from dual;
Rochelle cursor rc;
Begin
If (to_char (sysdate, 'dd') = 30) then
-- Ref cursor with dynamic SQL
Open l_cursor for 'select * from emp ';
Elsif (to_char (sysdate, 'dd') = 29) then
-- Ref cursor with static SQL
Open l_cursor for select * from dept;
Else
-- With ref cursor with static SQL
Open l_cursor for select * from dual;
End if;
-- The "normal" static cursor
Open c;
End;
/
In this Code block, you can see the most obvious difference: no matter how many times the code block is run, the cursor C is always select * from dual. Instead, the ref cursor can be any result set, because the "select * from emp" string can be replaced by a variable that actually contains any query.
In the above Code, a weak type of REF cursor is declared. Next, let's look at a strong (restricted) REF cursor, this type of REF cursor is also used in practical application systems.
Create table gsm_resource
(
Gsmno varchar2 (11 ),
Status varchar2 (1 ),
Price number (8, 2 ),
Store_id varchar2 (32)
);
Insert into gsm_resource values ('20170', '0', 13905310001, 'sd. JN.01 ');
Insert into gsm_resource values ('20170', '0', 13905312002, 'sd. JN.02 ');
Insert into gsm_resource values ('20170101', '1', 13905315005, 'sd. JN.01 ');
Insert into gsm_resource values ('20170', '0', 13905316006, 'sd. JN.03 ');
Commit;
SQL> declare
2 type gsm_rec is record (
3 gsmno varchar2 (11 ),
4 status varchar2 (1 ),
5 price number (8, 2 ));
6
7 type app_ref_cur_type is ref cursor return gsm_rec;
8 my_cur app_ref_cur_type;
9 my_rec gsm_rec;
10
11 begin
12 open my_cur for select gsmno, status, price
13 from gsm_resource
14 where store_id = 'sd. JN.01 ';
15 fetch my_cur into my_rec;
16 while my_cur % found loop
17 dbms_output.put_line (my_rec.gsmno | '#' | my_rec.status | '#' | my_rec.price );
18 fetch my_cur into my_rec;
19 end loop;
20 close my_cur;
21 end;
22/
13905310001 #0 #200
13905315005 #1 #500
PL/SQL procedure successfully completed
SQL>
There are also some differences between a common cursor and a REF cursor that everyone should be familiar with, so I will waste a bit of time.
1) PL/SQL static cursor cannot be returned to the client. Only PL/SQL can use it. The ref cursor can be returned to the client, which is the way to return the result set from the Oracle stored procedure.
2) the PL/SQL static cursor can be global, while the ref cursor is not. That is to say, the ref cursor cannot be defined outside the procedure or function in the package description or package body. It can be processed only when the ref cursor is defined, or returned to the client application.
3) The ref cursor can be transferred from the subroutine to the subroutine, but the cursor cannot. To share the static cursor, you must define it as a global cursor in the package description or package body. Because the use of global variables is not a good coding habit, you can use the ref cursor to share the cursor in PL/SQL without the need to mix global variables.
Finally, using a static cursor-through a static SQL statement (but without a ref cursor)-is more efficient than using a ref cursor, while using a ref cursor is limited to the following situations:
Return the result set to the client;
Share the cursor among multiple child routines (actually very similar to the one mentioned above );
When there are no other effective methods to achieve your goal, use the ref cursor, just as when dynamic SQL is required;
To put it simply, we should first consider using static SQL statements. The ref cursor is used only when the ref cursor is absolutely required. Some people suggest using implicit cursors as much as possible to avoid writing additional cursor control code (Declaration, open, get, close), and do not need to declare variables to save the data obtained from the cursor. This is because we have to decide the specific case.
Iv. cursor attributes
% FOUND: bool-TRUE if> 1 row returned
% NOTFOUND: bool-TRUE if 0 rows returned
% ISOPEN: bool-TRUE if cursor still open
% ROWCOUNT: int-number of rows affected by last SQL statement
Note: The usage of NO_DATA_FOUND and % NOTFOUND is different. The following is a summary:
1) The SELECT... INTO statement triggers NO_DATA_FOUND;
2) % NOTFOUND is triggered when the where clause of an explicit cursor is not found;
3) SQL % NOTFOUND is triggered when the where clause of the UPDATE or DELETE statement is not found;
4) Use % NOTFOUND or % FOUND in the Fetch loop of the cursor to determine the exit condition of the loop. Do not use NO_DATA_FOUND.
Differences between ref cursor and record in oracle
Cursor Is a cursor (or a pointer in some cases). It should point to the first address of data stored in the memory.
Record: Put the data directly.
How to Use ref cursor to process Oracle result sets
Type -------------------- -------- ------------ empno not null number (4) ENAME VARCHAR2 (10) JOB VARCHAR2 (9) mgr number (4) hiredate date sal number (7, 2) comm number (7, 2) deptno number (2) Finally, use ref cursor to obtain the result set output: SQL> set serveroutput on SQL> DECLARE 2 TYPE mytable IS TABLE OF emp % ROWTYPE; 3 l_data mytable; 4 l_refc sys_refcursor; 5 BEGIN 6 OPEN l_refc FOR 7 SELECT empno, ename, job, mgr, hiredate, sal, comm, deptno FROM emp; 8 9 FETCH l_refc bulk collect into l_data; 10 11 CLOSE l_refc; 12 13 FOR I IN 1 .. l_data.COUNT 14 LOOP 15 DBMS_OUTPUT.put_line (l_data (I ). ename 16 | 'was hired since '17 | l_data (I ). hiredate 18); 19 end loop; 20 END; 21/SMITH was hired since 17-DEC-80 ALLEN was hired since 20-FEB-81 WARD was hired since Dow JONES was hired since MARTIN was hired since between BLAKE was hired since 01-MAY-81 CLARK was hired since copyright SCOTT was hired since indexing KING was hired since 17-NOV-81 TURNER was hired since 08-SEP-81 ADAMS was hired since 23-MAY-87 JAMES was hired since FORD was hired since indexing MILLER was hired since 23 -JAN-82 PL/SQL procedure successfully completed. (responsible editor: Lu Zhaolin)