oracle之游标

先建两个表emp(员工表,员工号,所在部门号,名字,职位,工资)和dept(部门表,部门号,部门名称)


create table emp(empno char(4) constraint pk_emp_empno primary key,

deptno number(1) constraint fk_emp_dept_deptno references dept(deptno),
ename varchar(12),
job varchar(12),
sal number
);


create table dept(deptno number(1) constraint pk_dept_deptno primary key,
dname varchar2(20));

insert into dept values(1,'leader');
insert into dept values(2,'sale');
insert into dept values(3,'research');

        
insert into emp values('1111',2,'赵良万','saleman',3300    );
insert into emp values('1112',1,'邱晨  ','manager',3301    );
insert into emp values('1113',1,'王诗豪','manager',3302    );
insert into emp values('1114',1,'林雅娴','manager',3303    );
insert into emp values('1115',1,'黄松威','president',3304    );
insert into emp values('1116',3,'童宇翔','researchman',3305    );
insert into emp values('1117',3,'王智瑞','researchman',3306    );
insert into emp values('1118',3,'李沫寒','researchman',3307    );
insert into emp values('1119',3,'李维浩','researchman',3308    );
insert into emp values('1120',1,'罗子迪','manager',3309    );
insert into emp values('1121',1,'赵俊杰','manager',3310    );
insert into emp values('1122',1,'房亚鑫','manager',3311    );
insert into emp values('1123',2,'吴睿卿','saleman',3312    );
insert into emp values('1124',2,'王树声','saleman',3313    );
insert into emp values('1125',2,'郭佩强','saleman',3314    );
insert into emp values('1126',2,'周瑞阳','saleman',3315    );
insert into emp values('1127',2,'周倩  ','saleman',3316    );
insert into emp values('1128',2,'王真颖','saleman',3317    );
insert into emp values('1129',2,'王子旭','saleman',3318    );
    

 set serveroutput on;//可以在屏幕输出信息






1:显示职位为manager的员工的信息
declare

cursor c_job
is select empno,ename,job,sal
from emp where job='manager';
c_row c_job%rowtype;//可以省去,因为for循环里的in的作用
begin

for c_row in c_job loop
dbms_output.put_line(c_row.empno||' '||c_row.ename||' '||c_row.job||' '||c_row.sal);
end loop;
end;

2:

declare
cursor c_job
is select * from emp
where job='manager';
c_row c_job%rowtype;
begin
open c_job;
loop
fetch c_job into c_row;
exit when c_job%notfound;
dbms_output.put_line(c_row.empno||' '||c_row.ename||' '||c_row.job||' '||c_row.sal);
end loop;
close c_job;
end;


3:随便用一个update语句,看看隐式游标sql%notfound,sql%found,sql%isopen,sql%rowcount
begin
update emp set job='manger' where empno ='1111';
if sql%isopen then
  dbms_output.put_line('opening');
else
dbms_output.put_line('closing');
end if;

if sql%found then
  dbms_output.put_line('游标指向了有效行');
else
  dbms_output.put_line('novalues');  
end if;

dbms_output.put_line(sql%rowcount);

exception
when no_data_found then
  dbms_output.put_line('no data found');
when too_many_rows then
 dbms_output.put_line('too many rows');

end;




 
 declare
 empnumber emp.empno%type;
 empname emp.ename%type;
 begin
 if sql%isopen then
   dbms_output.put_line('cursor is openning');
 else
   dbms_output.put_line('cursor is closing');
 end if;
 if sql%notfound then
   dbms_output.put_line('not values');
 else
   dbms_output.put_line(empnumber);
 end if;
 dbms_output.put_line(sql%rowcount);
 dbms_output.put_line('-----------');
 select EMPNO,ENAME into  empNumber,empName from emp where EMPNO='1111';
 dbms_output.put_line(sql%rowcount);
 if sql%isopen then
   dbms_output.put_line('cursor is closing');
 else
   dbms_output.put_line('cursor is opening');
 end if;
 if sql%found then
   dbms_output.put_line(empnumber);
 else
   dbms_output.put_line('no values');
 end if;
 exception
 when no_data_found then
    dbms_output.put_line('No Value');
 when too_many_rows then
    dbms_output.put_line('too many rows');
 end;

   
4:使用游标和for 循环显示所有员工编号和姓名
declare
cursor c_emp is
select empno,ename from emp;
begin
for c_row in c_emp loop
  dbms_output.put_line('Empno:'||c_row.empno||' Ename:'||c_row.ename);
end loop;
end;



5:使用游标和while循环显示所有员工编号和姓名
(1)把游标所蕴含的变量分别into到相同类型的变量,把变量输出

declare
c_empno emp.empno%type;
c_name emp.ename%type;
cursor c_emp is
select empno,ename from emp;
begin
open c_emp;
fetch c_emp into c_empno,c_name;
while   c_emp%found  loop
  dbms_output.put_line('Empno:'||c_empno||' Ename:'||c_name);
  fetch c_emp into c_empno,c_name;
end loop;
close c_emp;
end;

6:使用游标和loop循环显示所有员工编号和姓名
(2)直接定义一个指向游标变量指向游标的一行数据
declare
cursor c_emp is
select empno,ename from emp;
c_row c_emp%rowtype;//定义一个游标变量指向c_emp游标的一行数据
begin
open c_emp;
loop
fetch c_emp into c_row;
exit when c_emp%notfound;
dbms_output.put_line('Empno:'||c_row.empno||' Ename:'||c_row.ename);
end loop;
close c_emp;
end;


7:使用有参数的游标显示指定部门名称的所有员工编号姓名
declare
cursor c_emp(deptname varchar) is
select empno,ename from emp
where deptno in(select deptno from dept where dname=deptname);
c_row c_emp%rowtype;

begin
for c_row in c_emp('sale') loop
dbms_output.put_line('Empno:'||c_row.empno||' Ename:'||c_row.ename);
end loop;

end;



8:使用游标来对 游标结果集合中当前行所对应的数据库进行delete或update操作
该需求迫使ORACLE锁定游标结果集合的行,
可以防止其他事务处理更新或删除相同的行,直到您的事务处理提交或回退为止。
语法:
/*nowait表示马上执行该程序,如果游标本该指向的结果集合已被其他事务锁定,则报错*/

SELECT column_list FROM table_list FOR UPDATE [OF column[, column]…] [NOWAIT]
where current of 游标变量 /*表示在该游标所在当前行*/


create table emp1 as select * from emp;
(1)
declare
cursor c_emp(deptname varchar) is
select * from emp1
where deptno in(select deptno from dept where dname=deptname) for update of sal nowait ;

newsal number;
c_row c_emp%rowtype;
begin
open c_emp('sale');
loop
fetch c_emp into c_row;
exit when c_emp%notfound;
if c_row.sal<1000 then
  newsal:=c_row.sal*5;
elsif c_row.sal<3000 then
  newsal:=c_row.sal*3;
else
  newsal:=c_row.sal*2;
end if;

update emp1 set sal=newsal where current of c_emp;
end loop;
close c_emp;
end;

(2)当然,也可以通过游标做一般的修改,只是在确定更新或删除的行时where 的判断条件要注意选择恰当

declare
cursor c_emp(deptname varchar) is
select * from emp1
where deptno in(select deptno from dept where dname=deptname);

newsal number;
c_row c_emp%rowtype;
begin
open c_emp('leader');
loop
fetch c_emp into c_row;
exit when c_emp%notfound;
if c_row.sal<1000 then
  newsal:=c_row.sal*5;
elsif c_row.sal<3000 then
  newsal:=c_row.sal*3;
else
  newsal:=c_row.sal*2;
end if;

update emp1 set sal=newsal where empno=c_row.empno;
end loop;
close c_emp;
end;



9:动态游标
declare
type emp_cursor is ref cursor;
my_cursor emp_cursor;
tab varchar2(100);
str varchar2(120);
c_row emp_cursor%rowtype;
begin
str = 'select * from '||tab;
open my_cursor for str;
loop
fetch my_cursor into c_row;
exit when my_cursor%notfound;
end loop;
end;

 





  • 1
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值