• Oracle 触发器,事物


    触发器:自动执行,可以实现表的约束。

    1.行级触发器:  

    CREATE OR REPLACE TRIGGER del_deptid
    AFTER DELETE ON  deptment        --触发器条件 DELETE动作
    FOR EACH ROW                     --循环每一行都改
    BEGIN
    DELETE FROM emp WHERE id=:old.id; --触发后动作
    END del_deptid;         --END;都行
    /    
    DELETE FROM deptment WHERE id='001';  --触发触发器
    CREATE OR REPLACE TRIGGER insert_dept
    AFTER INSERT ON  deptment        --触发器条件 INSERT动作
    FOR EACH ROW                     --循环每一行都改
    BEGIN
    INSERT INTO emp(eid ,ename,id) VALUES('121','qwer',:new.id); --触发后动作
    END;
    / 
      old new
    insert n y
    delete y n
    update y y

     n为不涉及的

     只有在创建触发器的时候会触及oracle的old和new逻辑表,old和new是oracle在内存中建立的表,表的字段结构和触发器所涉及的表的字段结构一致,对表操作时,先将要修改的内容保存在old和new中,commit后写到磁盘中,如删除表中的一条的数据,先将内存中该表的该条数据移动到old表中,插入是将要插入的数据先插入到new中,之后再插入到内存表中,更新是将where后的信息存入old,将set红的数据存入new中,其他不变字段就一样。

    利用old和new表做级联更新:

    CREATE OR REPLACE TRIGGER update_dept
    AFTER UPDATE ON deptment
    FOR EACH ROW
    BEGIN
    UPDATE emp SET id=:new.id WHERE id=:old.id;
    END;
    /          --不可以在语句块中写commit 和 rollback
    UPDATE deptment SET id='yy' WHERE id='01';
    CREATE OR REPLACE TRIGGER book_delete
    AFTER DELETE ON books
    FOR EACH ROW
    BEGIN 
    IF :old.books_id='0001' THEN                     --通过触发器实现控制
    RAISE_APPLICATION_ERROR(-20000,'不允许删除!');    ---2000为错误代码
    END IF;
    END;
    /

    2.语句级触发器:

    CREATE OR REPLACE TRIGGER dml_aa
    AFTER INSERT OR DELETE OR UPDATE         --可以是多个动作触发
    BEGIN                                       --没有for each row 没有数据完整性约束   
    IF INSERTING THEN
    INSERT INTO mylog VALUES(user,sysdate,'I');
    ELSIF DELETING THEN
    INSERT INTO mylog VALUES(user,sysdate,'D');
    ELSE
    INSERT INTO mylog VALUES(user,sysdate,'U');
    END IF;
    END;
    /

    3.利用触发器实现表中整型字段的自增:

    CREATE OR REPLACE TRIGGER set_no
    BEFORE INSERT ON auto              --前触发器,插入之前做一个预处理
    FOR EACH ROW
    DECLARE
    sn number(5);  --定义变量
    BEGIN
    SELECT myseq.nextval INTO sn FROM dual;--取出myseq序列的值,放入变量中
    :NEW.a:=sn;          --插入前,将sn的值赋给表中的a字段,NEW为触发器在内存中自动生成的和要处理的表字段结构一致的表,即auto表中的a字段,如果用向a字段。
    END;
    /

    4.替换触发器:

    有的视图是由两个表组成的,当视图是由两个或两个以上组成的是不允许同时更新的,而替换触发器可以解决这种视图的多表更新的,替换触发器在Oracle中只能建在视图上。

    视图建立在员工表和部门表上,v_emp_dept;

    当向视图中插入数据时会提示,每次只能更改一个表中的信息,用替换触发器解决此问题的方法。

    CREATE OR REPLACE TRIGGER tr_v_e_d
    INSTEAD OF INSERT ON v_emp_dept --替换向v_emp_dept 视图中插入数据的方法,分别向两个表中插入数据实现
    FOR EACH ROW                      --替换触发器是特别的行触发器
    BEGIN
    INSERT INTO deptment VALUES(:new.id,:new.name);
    INSERT INTO emp(eid,ename,sex,id) VALUES(:new.eid,:new.ename,:new.sex,:new.id);
    END;
    /

    事物

    修改表的时候如果不 commit 是不会修改的,虽然用查询语句查询会出现该条记录已被修改,但只是在内存中修改,用 rollback命令即可还原,只要没commit就没有修改该表。commit 是将内存中的数据写到磁盘上,rollback命令可还原上一个动作的的修改,一旦commit之后,就不可以rollback回来了,rollback之后也不可以commit了。

    SELECT * FROM  dept FOR UPDATE;
    这样在其他用户下就不可以修改该表,直到你修改之后,commit,别人才可以改,像是买票那个锁。
  • 相关阅读:
    多线程编程(2):线程的同步
    C#中listview实现排序
    [PLC]S7-300的数据类型
    C# 多线程编程(4):多线程与UI操作
    Thunderbird 80 column FIX 发出的邮件也需要在80列处line break
    vsftp 500 OOPS: vsftpd: refusing to run with writable anonymous root
    科普 What is YUV
    转载:网站真的可以无密码登录么?
    Ubuntu 12.04安装Microsoft lifecam studio摄像头
    Thunderbird on Ubuntu 12.04 调整邮件列表行间距
  • 原文地址:https://www.cnblogs.com/weixiaole/p/3258480.html
Copyright © 2020-2023  润新知