Oracle 学习笔记 16 -- 游标(PL/SQL)
在PL/SQL程序中,对于处理多行记录的事务经常使用游标来实现。当执行查询语句或者数据操纵语句是,一般可能会产生或者处理一组记录。游标是为了处理这些记录而分配的一段内存区。
游标分为:显示游标和隐示游标。当记录集中只有单行数据时,系统自动的进行定义右边,称为隐示游标。记录集中含有多行数据时,需要用户自己定义游标,称为显示游标。下面分别进行介绍。
显示游标
显示游标的处理需四个使用步骤:
1.定义游标:
就是定义一个游标名,以及与其对应的select 语句。
格式:
CURSOR cursor_name is select_statement 。
2.打开游标:
游标定义之后,要使用游标中的数据,就要打开游标。使用OPEN打开游标。游标只能打开一次。
格式:
OPEN cursor_name 。
3.提取游标数据:
检索游标结果集中的数据,放入指定的变量之中。
格式:
FETCH cursor_name INTO variable_name 。
4.关闭游标:
游标使用完成之后,应该及时的关闭游标,将系统资源释放。
格式:
CLOSE cursor_name 。
游标属性
%found :布尔型,判断最近一次执行fetch语句后,是否从缓冲区中提取到数据,如果提取到数据,返回TURE,否则返回false。
%notfound:布尔型,与%found相反,没有提取到数据返回true,否则返回false。
%ISOPEN :布尔型,当游标打开的时候返回true。
%ROWCOUNT:数字型,放回已从游标中读取的记录数。
例:使用游标数据10号部门的员工工资。
declare
--定义变量
v_sal emp.sal%type ;
--定义游标
cursor emp_sal_cursor is select sal from emp where deptno = 10 ;
begin
--打开游标
open emp_sal_cursor ;
--提起游标信息
fetch emp_sal_cursor into v_sal ;
while emp_sal_cursor%found loop
dbms_output.put_line(v_sal);
fetch emp_sal_cursor into v_sal ;
end loop ;
--关闭游标
close emp_sal_cursor;
end ;
例:使用记录类型和游标检索数据
declare
--定义变量
typeemp_record is record(
v_salemp.sal%type ,
v_idemp.empno%type
);
v_emp_record emp_record ;
--定义游标
cursor emp_sal_cursor is selectsal ,empno from emp where deptno = 10 ;
begin
--打开游标
openemp_sal_cursor ;
--提起游标信息
fetch emp_sal_cursor into v_emp_record ;
while emp_sal_cursor%found loop
dbms_output.put_line(v_emp_record.v_sal ||‘, ‘|| v_emp_record.v_id);
fetch emp_sal_cursor into v_emp_record ;
end loop ;
--关闭游标
close emp_sal_cursor;
end ;
游标的FOR循环
PL/SQL语言提供了游标for循环语句,自动执行游标的OPEN,FETCH,CLOSE语句和循环语句的功能,当进入循环式,游标for循环语句自动打开,并提取第一行游标数据,当程序处理完当前所提取的数据而进入下一次循环式,游标for循环语句自动的提取下一行的数据,当提取晚结果集合中所有的数据行后自动结束循环,并自动关闭游标。
格式:
for index_var in cursor_name loop
--处理代码
end loop ;
例:使用for循环检索数据
declare
--定义游标
cursor emp_sal_cursor is select * from emp where deptno = 10 ;
begin
for c in emp_sal_cursor loop
dbms_output.put_line(c.sal ||‘, ‘|| c.hiredate);
end loop ;
end ;
例:使用游标和for循环更新数据
declare
cursoremp_sal_cursorisselect empno,sal fromemp ;
v_empnumber(4 ,2 ) ;
begin
forcinemp_sal_cursorloop
ifc.sal <1000thenv_emp := 0.05 ;
elsifc.sal <2000thenv_emp := 0.03 ;
elsifc.sal <5000thenv_emp := 0.02 ;
elsev_emp := 0.01 ;
endif ;
dbms_output.put_line(c.sal ||‘,‘|| c.empno);
updateempsetsal = sal* (1+ v_emp) whereempno = c.empno ;
endloop ;
end ;
带参数的游标
游标在定义的时候,可以带参数。参数在指定数据类型时,不能指定它的长度。
例:当声明的游标带有参数时,通过游标for循环语句来为游标传递参数
declare
cursor c_emp(dept_no number ) is select sal , ename from
emp here deptno = dept_no ;
begin
for c in c_emp(20) loop
dbms_output.put_line(c.sal || ‘,‘||c.ename);
end loop ;
end隐示游标
不需要显示的定义游标。调用格式:SQL% ;
begin
update emp set sal = sal +100 where empno = 7444 ;
if sql%notfound then dbms_output.put_line(‘没有此人‘);
end if ;
end