注册 | 登录 |
地方论坛门户及新闻和人才网址大全

Oracle显示游标的使用及游标for循环

时间:2021-07-21人气:-


本篇文章给大家介绍oracle显示游标的使用及游标for循环,当查询返回单行记录时使用隐式游标,查询返回多行记录并逐行进行处理时使用显式游标,对本文感兴趣的朋友一起学习吧

下面给大家介绍在什么情况下用隐式游标,什么情况下用显示游标:

1.查询返回单行记录时→隐式游标;

2.查询返回多行记录并逐行进行处理时→显式游标

--显示游标属性

  1. declareCURSORcur_empISSELECT*FROMemp;
  2. row_empcur_emp%ROWTYPE;BEGIN
  3. OPENcur_emp;FETCHcur_empINTOrow_emp;
  4. WHILEcur_emp%FOUNDLOOP
  5. dbms_output.put_line(row_emp.empno||'----'||row_emp.ename);FETCHcur_empINTOrow_emp;
  6. ENDLOOP;closecur_emp;
  7. END;

--使用显式游标修改数据(给所有的部门经理加薪1000)

  1. DECLARECURSORemp_curIS
  2. SELECTempno,ename,salFROMempWHEREjob='MANAGER'FORUPDATE;emp_rowemp_cur%ROWTYPE;
  3. BEGINOPENemp_cur;
  4. LOOPFETCHemp_curINTOemp_row;
  5. IFemp_cur%NOTFOUNDTHENEXIT;
  6. ELSEUPDATEempSETsal=sal+1000WHERECURRENTOFemp_cur;
  7. ENDIF;ENDLOOP;
  8. COMMIT;CLOSEemp_cur;
  9. END;

·注意:

1、如果游标打开之前或关闭之后,使用游标属性,Oracle会抛出一个INVALID_CURSOR错误(ORA-01001);

2、如果在第一次fetch后结果集是空的,%found=false,%NotFound=true,%ROWCOUNT=0;

3、如果使用了BULK COLLECT,那么%ROWCOUNT的值可能不是0或1,实际上他返回的是提取到相关集合的行数。

--游标for循环(给所有的部门经理减薪1000)

  1. DECLARECURSORemp_curIS
  2. SELECTempno,ename,salFROMempWHEREjob='MANAGER'FORUPDATE;BEGIN
  3. FORemp_rowINemp_curLOOP
  4. UPDATEempSETsal=sal-1000WHERECURRENTOFemp_cur;ENDLOOP;
  5. COMMIT;END;

--我们可以看到游标FOR循环确实很好的简化了游标的开发,我们不在需要open、fetch和close语句,不在需要用%FOUND属性检测是否到最后一条记录,这一切Oracle隐式的帮我们完成了。

--给经理加薪5000,其他加薪1000

  1. DECLARECURSORemp_curIS
  2. SELECT*FROMempFORUPDATE;BEGIN
  3. FORemp_rowINemp_curLOOP
  4. IFemp_row.job='MANAGER'THENUPDATEempSETsal=sal+5000WHERECURRENTOFemp_cur;
  5. ELSEUPDATEempSETsal=sal+1000WHERECURRENTOFemp_cur;
  6. ENDIF;ENDLOOP;
  7. END;

下面给大家介绍oracle游标cursor简单使用

总共介绍两种游标一种高效使用游标cursor 、sys_refcursor 、 bulk collect

1、cursor游标使用

  1. /*简单cursor游标*students表里面有name字段,你可以换做其他表测试
  2. */--定义
  3. declare--定义游标并且赋值(is不能和cursor分开使用)
  4. cursorstus_curisselect*fromstudents;--定义rowtype
  5. cur_stustudents%rowtype;/*开始执行*/
  6. begin--开启游标
  7. openstus_cur;--loop循环
  8. loop--循环条件
  9. exitwhenstus_cur%notfound;--游标值赋值到rowtype
  10. fetchstus_curintocur_stu;--输出
  11. dbms_output.put_line(cur_stu.name);--结束循环
  12. endloop;--关闭游标
  13. closestus_cur;/*结束执行*/
  14. end;

执行结果

  1. SQL>declare--定义游标并且赋值(is不能和cursor分开使用)
  2. cursorstus_curisselect*fromstudents;--定义rowtype
  3. cur_stustudents%rowtype;/*开始执行*/
  4. begin--开启游标
  5. openstus_cur;--loop循环
  6. loop--循环条件
  7. exitwhenstus_cur%notfound;--游标值赋值到rowtype
  8. fetchstus_curintocur_stu;--输出
  9. dbms_output.put_line(cur_stu.name);--结束循环
  10. endloop;--关闭游标
  11. closestus_cur;/*结束执行*/
  12. end;/
  13. 杨过
  14. 郭靖付政委
  15. 刘自飞江风
  16. 任我行任盈盈
  17. 令狐冲韦一笑
  18. 张无忌朵儿
  19. 谢逊小龙女
  20. 欧阳锋欧阳锋

2、sys_refcursor游标使用

  1. /**游标名:sys_refcursor
  2. *特别注意赋值方式:for*与上重复内容不在叙述
  3. */declare
  4. stu_cursys_refcursor;stuonestudents%rowtype;
  5. begin
  6. --这句赋值方式foropenstu_curforselect*fromstudents;
  7. --fetch赋值给rowtypefetchstu_curintostuone;
  8. loop
  9. dbms_output.put_line(stuone.name||''||stuone.hobby);fetchstu_curintostuone;
  10. exitwhenstu_cur%notfound;endloop;
  11. end;

执行结果

  1. SQL>/**游标名:sys_refcursor
  2. *特别注意赋值方式:for*与上重复内容不在叙述
  3. */declare
  4. stu_cursys_refcursor;stuonestudents%rowtype;
  5. begin--这句赋值方式for
  6. openstu_curforselect*fromstudents;--fetch赋值给rowtype
  7. fetchstu_curintostuone;loop
  8. dbms_output.put_line(stuone.name||''||stuone.hobby);fetchstu_curintostuone;
  9. exitwhenstu_cur%notfound;endloop;
  10. end;/
  11. 杨过保护小龙女郭靖修炼降龙十八掌
  12. 付政委看小人书刘自飞编程写代码
  13. 江风编程写代码任我行修炼神功
  14. 任盈盈游山玩水令狐冲行侠仗义
  15. 韦一笑吸拾人雪张无忌修行
  16. 朵儿洗浴谢逊毕生研究屠龙刀
  17. 小龙女修炼玉女心经欧阳锋看小人书

补充一种循环条件

  1. declarestu_cursys_refcursor;
  2. stuonestudents%rowtype;begin
  3. openstu_curforselect*fromstudents;fetchstu_curintostuone;
  4. --特别注意循环条件的改变--这个条件是发现了在循环
  5. --与上一个notfound不同的whilestu_cur%foundloop
  6. dbms_output.put_line(stuone.name||''||stuone.hobby);fetchstu_curintostuone;
  7. endloop;end;

--普通的fetch into

  1. /*普通方式*/declare
  2. cursormyemp_curisselect*frommyemp;v_myempmyemp%rowtype;
  3. beginopenmyemp_cur;
  4. fetchmyemp_curintov_myemp;whilemyemp_cur%foundloop
  5. dbms_output.put_line(v_myemp.ename);fetchmyemp_curintov_myemp;
  6. endloop;end;

--高效的bulk collect

  1. /*高效bulkcollectfor*/declare
  2. cursormyemp_curisselect*frommyemp;
  3. typemyemp_tabistableofmyemp%rowtype;myemp_rdmyemp_tab;
  4. beginopenmyemp_cur;
  5. loopfetchmyemp_curbulkcollectintomyemp_rdlimit20;
  6. foriin1..myemp_rd.countloopdbms_output.put_line('姓名:'||myemp_rd(i).ename);
  7. endloop;exitwhenmyemp_cur%notfound;
  8. endloop;end;


注:相关教程知识阅读请移步到oracle教程频道。

上篇:如何快速提高网站收录 提升网站快速收录的解决方法

下篇:帝国cms专题页面点击率统计代码