C/C++教程

Oracle视图、触发器和索引

本文主要是介绍Oracle视图、触发器和索引,对大家解决编程问题具有一定的参考价值,需要的程序猿们随着小编来一起学习吧!

一. 视图和物化视图

  1. 普通视图:可以将一条select语句的结果保存成一张虚表

     虚表:表中不会保存具体的数据,只是用来保存查询的sql语句

     (1)简单的视图:主要是针对一张表的查询操作创建的视图

     (2)复杂的视图:主要查询的结果来自于多张表关联

     视图的创建语法:

      create [or replace] view 视图名称[(列名,列名,...)]

      as

       select 查询语句;

       [with read only];

     例子:

      create or replace view view_emp

      as

       select e.*,row_number() over(order by sal desc) from emp e;

      select * from view_emp;

     优点:

      (1)简化sql语句的查询操作

      (2)可以对表中的数据起到保护作用

  2. 物化视图

    作用:提高查询效率

     物化视图又叫做实体化的视图,是真实保存的数据,相当于某一些表的一个副本

     物化视图是真实的占用物理存储空间,对物化视图的操作就相当于对一张表的操作,但是物化视图不支持增删改

    关键字:matetialized view

    创建物化视图的语法:

     create materialized view 视图名

     [build immediate|build deferred]

     [refresh fast|complete|force] 

     [on commit|demand] | start with 开始刷新时间 next 下一次刷新的时间

     [with primary key|rowid]

     as

      select 语句;

    

     build immediate|build deferred:是否立即生成数据

      build immediate:在创建物化视图的时候会立即生成数据(默认情况)

      build deferred:在创建的时候并不会生成数据,而是在后续使用的过程中生成数据

     refresh fast|complete|force:设置更新方式

      fast:会进行增量更新,只会更新发生改变的数据

      complete:会进行全量更新,会刷新所有数据

      force:系统会自动进行判断,然后选择合适的刷新方式

     on commit|demand | start with:设置刷新时机

      commit:在原表修改了之后提交事务的时候进行刷新

      demand:需要手动刷新(默认情况)

      start with:设置在某个时间段内自动刷新,其实就是相当于在数据库中创建了一个定时任务,视图删除了之后定时任务也会被删除。

     with primary key|rowid:

      设置在进行增量的时候是根据主键进行判断还是根据rowid判断,默认为主键

 

    手动刷新物化视图:

     begin

      dbms_mview.refresh('物化视图名','C');

     end;

    使用物化视图进行增量刷新:

    注意:1. 如果要进行增量刷新,必须要为该表创建一个视图日志

       2. 一个表只能创建一个视图日志

       3. 视图日志由系统自己创建名称,名称为mlog$_表名

       4. 在创建增量刷新的物化视图的时候判定依据必须要和视图日志中指定的保持一致。

    视图日志的创建方式:

    create materialized view log on 表名 [with primary key|rowid];

    创建增量的物化视图:

    create materialized view v_m_dept

    refresh fast

    on commit

    with primary key

    as

     select * from emp;

    删除物化视图:

     drop materialized view 视图名

    删除视图日志:

     drop materialized view log on 表名

二. 触发器:trigger

  可以看做是一种特殊的存储过程,触发器不是由用户自己调用,而是由系统去调用

  1. 创建触发器:

   create [or replace] trigger 触发器名称

   before|after|instead of 触发事件

   on 表名|视图|用户模式

   [for each row]

   begin

    触发器执行所需要的代码

   end;

   before|after|instead of:触发时机

   触发事件:insert update delete create drop alter

   触发器分类:

    (1)语句级别触发器

      触发器执行次数和执行的sql语句的条数有关,一般就是执行一条sql语句,触发器就会执行1次

      例子:

       创建一个表用来记录数据库中dept表的操作

        create table dept_log(

          oper_type varchar2(20),

          oper_date date

        )

       编写触发器,用来记录对dept表的操作

        create or replace trigger tri_dept

        before insert or update or delete

        on dept

        declare

         oper_type varchar2(20);

        begin

         if inserting then

          oper_type:='添加';

         elsif updating then

          oper_type:='更新';

         elsif deleting then

          oper_type:='删除';

         else

          oper_type:='其他';

         end if;

         insert into dept_log values(oper_type,sysdate);

        end tri_dept;

    (2)行级触发器

      触发器执行的次数和sql语句执行影响的行数有关

      行级触发器必须设置:for each row

      行级触发器中两个常见的关键字:

      :new 代表新的一行的数据,如果要访问新的一列的字段可以使用:new.字段名

        :new 只能使用在 insert 和 update 中

      :old 代表原来的一行数据,如果要访问原来的行中的字段值可以使用:old.字段名

        :old 只能使用在 delete 和 update 中

      例子:

       编写一个触发器来实现表中的主键自增长的功能

        create table user_t(

          u_id number,

          u_name varchar2(20);

        )

        create sequence seq_user;

        create or replace trigger tri_user

        before insert

        on user_t

        for each row

        begin

         select seq_user.nextval into :new.u_id from dual;

        end tri_user;

        测试触发器

        insert into user_t(u_name) values('小明');

    (3)替换触发器

      专门进行操作视图

      一般情况下对于多表关联的一些视图是不能进行修改或者添加操作,所以可以借助替换触发器来实现修改或添加

      注意:替换触发器的触发时机必须是instead of,替换触发器也是行级触发器,必须要执行for each row

      例子:

       使用替换触发器来完成向视图中的多个基表添加数据

        create or replace trigger tri_view

        instead of insert

        on v_emp_dept

        for each row

        begin

         insert into dept values(:new.deptno,:new.dname,:new.loc);

         insert into emp values(:new.empno,:new.ename,:new.job,:new.mgr,:new.hiredate,:new.sal,:new.comm,:new.deptno);

        end tri_view;

        insert into v_emp_dept values(9999,'LILY',);

    (4)用户系统级别的触发器

      主要就是触发器的添加对象是一个用户模式

      例子:

       创建一张表记录日志信息

        create table user_log(

          oper_type varchar2(20),  

          oper_name varchar2(20),

          oper_event varchar2(20),

          oper_user varchar2(20),

          oper_date date

        );

       记录当前用户对当前数据库对象的一些操作信息

        create or replace trigger tri_userlog

        before create or alter or drop

        on scott.schema

        begin

         insert into user_log values(

          sys.dictionary_job_type,

          sys.dictionary_job_name,

          ora_sysevent,

          sys.dictionary_obj_owner,

          sysdate

         );

        end tri_userlog;

        测试触发器

        drop table user_t;

 

三. 索引:index

  作用:提高查询效率。

  在创建表的时候如果给表设置主键,则系统或人 为主键列创建一个索引

  1. 创建索引的语法

   create [bitmap] index 索引名 on 表名(列名,列名,...)

   [reverse] [tablespace 表空间名]

   创建索引的原则:创建的索引如果不合理,不光不能提高查询效率,反而会降低DML效率

    (1)不建议在小表上创建索引

    (2)如果某一个字段经常会出现在 where 语句后面,则可以在该字段上创建索引

    (3)限制表上索引的个数

    (4)如果表中的某一些字段要经常进行排序操作,可以创建索引

    (5)一般在表进行关联的时候提高关联效率,会在关联的字段上创建索引

    (6)如果一个表经常进行DML操作,很少查询,则不建议创建索引

    (7)如果索引和表放在同一个表空间,则方便管理,如果他们放在不同的表空间,查询效率会比较高

   索引的分类:

    (1)B树索引:B-tree,是数据库中默认的索引方式,字段的重复率比较低,则可以使用B树索引

    (2)反向键索引:是特殊的B数索引,如果索引字段在分配的时候某一个数据比较集中,这时候如果用常规的索引会出现数据倾斜,则可以使用反向键索引

    (3)位图索引:关键字bitmap,专门用在一些重复率较高的字段上创建索引

    (4)函数索引:如果要经常基于某一个函数进行查询操作,则可以在该函数上创建索引

   例子:

    create index index_user on user_t(u_id);

    create index index_user on user_t(u_id) reverse;

    create bitmap index index_user on user_t(u_name) ;

    create index index_user on user_t(u_name) ;

这篇关于Oracle视图、触发器和索引的文章就介绍到这儿,希望我们推荐的文章对大家有所帮助,也希望大家多多支持为之网!