declare
--定义游标
cursor cur_xsjbxx is
select * from student order by sno;
--定义记录变量
ls_curinfo cur_xsjbxx%rowtype;
begin
open cur_xsjbxx;--打开游标
loop
FETCH cur_xsjbxx
INTO ls_curinfo;--获取记录值
EXIT WHEN cur_xsjbxx%NOTFOUND;--循环结束的条件:判断是否还有记录
dbms_output.put_line('学号:' || ls_curinfo.sno|| ',姓名:' || ls_curinfo.SNAME);
end loop;
close cur_xsjbxx;--关闭游标
end;
运行结果:
学号:s001,姓名:张三
学号:s002,姓名:李四
学号:s003,姓名:吴鹏
学号:s004,姓名:琴沁
学号:s005,姓名:王丽
学号:s006,姓名:李波
学号:s007,姓名:刘玉
学号:s008,姓名:萧蓉
学号:s009,姓名:陈萧晓
学号:s010,姓名:陈美
学号:s011,姓名:张三
学号:s012,姓名:即墨寒霜
学号:s013,姓名:张德坤
--%ROWCOUNT(游标计数器)
declare
--定义游标
cursor cur_xsjbcount is select * from student order by sno;
--定义记录变量
ls_curinfo cur_xsjbcount%rowtype;
begin
open cur_xsjbcount;--打开游标
loop
FETCH cur_xsjbcount
INTO ls_curinfo;--获取记录值
EXIT WHEN cur_xsjbcount%NOTFOUND;
--利用游标计数器打印学生个数
end loop;
dbms_output.put_line('表中一共有:'||cur_xsjbcount%ROWCOUNT||'个学生');
close cur_xsjbcount;--关闭游标
end;
运行结果:
表中一共有:13个学生
create [or replace] tigger 触发器名 触发时间 触发事件
on 表名
[for each row]
begin
pl/sql语句
end
解释:
触发器名 : 触发器对象的名称。由于触发器是数据库自动执行
的,因此该名称只是一个名称,没有实质的用途。
触发时间 : 指明触发器何时执行,该值可取。
before : 表示在数据库动作之前触发器执行。
after : 表示在数据库动作之后触发器执行。
触发事件 : 指明哪些数据库动作会触发此触发器。
insert : 数据库插入会触发此触发器;
update : 数据库修改会触发此触发器;
delete : 数据库删除会触发此触发器。
表 名 : 数据库触发器所在的表。
for each row:对表的每一行触发器执行一次。如果没有这
一选项,则只对整个表执行一次。
代码案例:
CREATE OR REPLACE TRIGGER ordeinfo_trigger
BEFORE UPDATE OR DELETE OR INSERT
ON orderinfo
BEGIN
--sysdate代指当前系统时间,为星期一,sysdate+5代指星期六
IF to_char(sysdate+5,'day') IN ('星期六','星期日') THEN
RAISE_APPLICATION_ERROR(-20008,'不允许在周六周日修改orderinfo表');
--打印错误信息:第一个参数为设定不同的错误信息标识代码
--(可以是20001-29999之间),第二个参数是提示出来的错误信息,
--大小可以是2k,但是超过2k按2k保留
END IF;
END;
--测试自定义触发器orderinfo_trigger时候起作用了
update orderinfo set message='new message ' where id='001';
CREATE OR REPLACE TRIGGER SAL_EMP
BEFORE UPDATE ON tg_user
FOR EACH ROW
BEGIN
IF :OLD.score > :NEW.score THEN
--DBMS_OUTPUT.PUT_LINE('积分减少');
RAISE_APPLICATION_ERROR(-20008,'积分不能减少');
ELSIF :OLD.score < :NEW.score THEN
DBMS_OUTPUT.PUT_LINE('积分增加');
ELSE
DBMS_OUTPUT.PUT_LINE('积分未作任何变动');
END IF;
DBMS_OUTPUT.PUT_LINE('更新前积分 :' || :OLD.score);
DBMS_OUTPUT.PUT_LINE('更新后积分 :' || :NEW.score);
END;
-- 测试一下 我们减一下积分,就会触发 我们写的触发器,就会报错
UPDATE tg_user SET score = -3000;
--测试一下,我们增加积分,触发器正常通过,就不会报错
UPDATE tg_user SET score = 60000 ;
6.触发器的增删改查
--【禁用某个触发器】ALTER TRIGGER <触发器名> DISABLE
ALTER TRIGGER SAL_EMP DISABLE
--【重新启用触发器】ALTER TRIGGER <触发器名> ENABLE
ALTER TRIGGER SAL_EMP ENABLE
--【启用表的所有触发器】ALTER TABLE <表名> ENABLE ALL TRIGGERS;
ALTER TABLE tg_user ENABLE ALL TRIGGERS;
--【删除触发器】DROP TRIGGER <触发器名>;
DROP TRIGGER SAL_EMP;