`
wangyanlong0107
  • 浏览: 499846 次
  • 性别: Icon_minigender_1
  • 来自: 沈阳
社区版块
存档分类
最新评论

oracle--ORA:04091:触发器/函数不能读它

 
阅读更多

   第一次写触发器,就有bug了

   前台用ajax保存用户的修改和删除,这时需求要加个触发器,在修改和删除时修改其他表的字段,加完触发器,点保存,前台弹出js错误,以为是js写的有误,结果查了半天js发现是ajax返回是出错。

   后台则为:2012-02-28 13:05:11,960 WARN [http-8080-Processor23] [RequestProcessor] Unhandled Exception thrown: class org.springframework.jdbc.BadSqlGrammarException。

    原来还是触发器有问题,用PL/SQL写的触发器,没有测试,最后不用程序单走触发器,测试了一下触发器,发现提示错误信息为:ora-04091:表TB_J DF_XC.....发生了变化,触发器/函数不能读它。

    写的触发器如下:用PL/SQL developer写的触发器

    CREATE OR REPLACE TRIGGER TB_PER_POSITONLEVEL_TRI

AFTER INSERT OR UPDATE OF c_effectivedate,c_postionlevel,c_postioncluster OR DELETE ON TB_PER_POSITONLEVEL 
FOR EACH ROW
BEGIN
     IF inserting THEN
        UPDATE tb_inf_employee t SET t.c_positionlevel = ( SELECT c_postionlevel FROM (SELECT a.c_postionlevel FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY a.c_effectivedate DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ),
                                     t.c_positionorder = ( SELECT c_postioncluster FROM (SELECT a.c_postioncluster FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY a.c_effectivedate DESC,a.c_operatetime DESC) WHERE ROWNUM =1 );
     END IF;
     IF deleting THEN
        UPDATE tb_inf_employee t SET t.c_positionlevel = ( SELECT c_postionlevel FROM (SELECT a.c_postionlevel FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid ORDER BY a.c_effectivedate DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ),
                                     t.c_positionorder = ( SELECT c_postioncluster FROM (SELECT a.c_postioncluster FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid ORDER BY a.c_effectivedate DESC,a.c_operatetime DESC) WHERE ROWNUM =1 );
     END IF;
     IF UPDATing THEN
        UPDATE tb_inf_employee t SET t.c_positionlevel = ( SELECT c_postionlevel FROM (SELECT a.c_postionlevel FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid ORDER BY a.c_effectivedate DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ),
                                     t.c_positionorder = ( SELECT c_postioncluster FROM (SELECT a.c_postioncluster FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid ORDER BY a.c_effectivedate DESC,a.c_operatetime DESC) WHERE ROWNUM =1 );
     END IF;                               
END TB_PER_POSITONLEVEL_TRI;

 

--手动 insert update delete测试

SELECT * FROM TB_PER_POSITONLEVEl r WHERE r.c_empoid = '853949' FOR UPDATE --853949

SELECT * FROM tb_inf_employee t WHERE t.c_employeeid = '853949'


   上网搜索了一天触发器,答案不给力,后来搜索ORA-04091有了眉目,以后oracle的问题,直接搜索问题编号就好了

   结果如下:代码涉及到对关联表的数据操作,比如查询关联表的总记录数或者往关联表中插入一条记录,该类型代码只能在语句级触发器中使用,如果在行级触发器中使用,将会报ORA-04091错误oracle的意思是要是涉及子查询说明你数据库设计上就有问题!

   那我又要用行级触发器咋么办呢?

方法一:新建了与orginfo结构完全相同的临时表tmp_orginfo,使得在orginfo上的触发器读写tmp_orginfo,再用tmp_orginfo上的触发器写回orginfo,解决ora-04091问题。

方法二:开启自治事务

   oracle行级触发器无法读取当前表的数据,为达到操作本表的效果建议开启自治事务
create or replace trigger TRI_ACTION_LOG

after insert on action_log
for each row
declare
PRAGMA AUTONOMOUS_TRANSACTION;
co integer;
begin
    select count(1) into co from action_log;
    :new.log_state:=co;
    insert into action_log(log_state)
    values(:New.log_state);
    commit;
end;

把子查询放到中间变量里面,并用自治事务修改如下:


   CREATE OR REPLACE TRIGGER TB_PER_POSITONLEVEL_TRI

AFTER INSERT OR UPDATE OF c_effectivedate,c_postionlevel,c_postioncluster OR DELETE ON TB_PER_POSITONLEVEL

FOR EACH ROW

DECLARE

position_effdate DATE;

position_level varchar2(64);

position_order varchar2(64);

position_oid varchar2(128);

cou NUMBER(3);

PRAGMA AUTONOMOUS_TRANSACTION;

BEGIN

     --SELECT COUNT(*) INTO cou FROM (SELECT a.c_oid FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC);

     --INSERT INTO A_TEMP VALUES(cou);

     IF inserting THEN

        SELECT COUNT(*) INTO cou FROM (SELECT a.c_oid FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC);

 

       -- INSERT INTO A_TEMP VALUES('行级别触发器after');

        --INSERT INTO A_TEMP VALUES(position_oid);

        --INSERT INTO A_TEMP VALUES( to_char(position_effdate,'fmdd month yyyy') );

        --INSERT INTO A_TEMP VALUES(position_level);

        --INSERT INTO A_TEMP VALUES(position_order);

        --INSERT INTO A_TEMP VALUES(cou);

        IF cou <> 0 THEN

           SELECT CASE WHEN :new.c_oid = c_oid THEN :NEW.c_postionlevel ELSE c_postionlevel END INTO position_level FROM (SELECT a.c_oid, a.c_postionlevel FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC)  WHERE ROWNUM =1 ;

           SELECT CASE WHEN :new.c_oid = c_oid THEN :NEW.c_effectivedate ELSE c_effectivedate END INTO position_effdate FROM (SELECT a.c_oid,a.c_effectivedate FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

           SELECT CASE WHEN :new.c_oid = c_oid THEN :new.c_postioncluster ELSE c_postioncluster END INTO position_order FROM (SELECT a.c_oid,a.c_postioncluster FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

           SELECT c_oid INTO position_oid FROM (SELECT a.c_oid FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

 

           IF position_effdate <= :NEW.c_effectivedate THEN

              --INSERT INTO A_TEMP VALUES('插入的是最新的');

              UPDATE tb_inf_employee t SET t.c_positionlevel = :NEW.c_postionlevel,

                                      t.c_positionorder = :NEW.c_postioncluster WHERE t.c_employeeid = :NEW.C_EMPOID;

            END IF;

            ELSIF position_effdate > :NEW.c_effectivedate THEN

              --INSERT INTO A_TEMP VALUES('插入的不是最新的,没有影响');

              UPDATE tb_inf_employee t SET t.c_positionlevel = position_level,

                                      t.c_positionorder = position_order WHERE t.c_employeeid = :NEW.C_EMPOID;

 

            END IF;

        END IF;

        IF cou = 0 THEN

           UPDATE tb_inf_employee t SET t.c_positionlevel = :NEW.c_postionlevel,

                                      t.c_positionorder = :NEW.c_postioncluster WHERE t.c_employeeid = :NEW.C_EMPOID;

        END IF;

     IF deleting THEN

        SELECT COUNT(*) INTO cou FROM (SELECT a.c_oid FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC);

 

       -- INSERT INTO A_TEMP VALUES('行级别触发器after');

        --INSERT INTO A_TEMP VALUES(position_oid);

       -- INSERT INTO A_TEMP VALUES( to_char(position_effdate,'fmdd month yyyy') );

       -- INSERT INTO A_TEMP VALUES(position_level);

        --INSERT INTO A_TEMP VALUES(position_order);

      --  IF(:OLD.c_oid == )

        IF cou <> 1 THEN

        SELECT c_postionlevel INTO position_level FROM (SELECT a.c_postionlevel FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid AND a.c_oid <> :old.c_oid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

        SELECT c_effectivedate INTO position_effdate FROM (SELECT a.c_effectivedate FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid AND a.c_oid <> :old.c_oid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

        SELECT c_postioncluster INTO position_order FROM (SELECT a.c_postioncluster FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid AND a.c_oid <> :old.c_oid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

        SELECT c_oid INTO position_oid FROM (SELECT a.c_oid FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :OLD.c_empoid AND a.c_oid <> :old.c_oid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

        UPDATE tb_inf_employee t SET t.c_positionlevel = position_level,

                                     t.c_positionorder = position_order WHERE t.c_employeeid = :OLD.C_EMPOID;

        END IF;

        IF cou = 1 THEN

        UPDATE tb_inf_employee t SET t.c_positionlevel = '',

                                     t.c_positionorder = '' WHERE t.c_employeeid = :OLD.C_EMPOID;

        END IF;

     END IF;

     IF UPDATing THEN

        SELECT CASE WHEN :new.c_oid = c_oid THEN :NEW.c_postionlevel ELSE c_postionlevel END INTO position_level FROM (SELECT a.c_oid, a.c_postionlevel FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC)  WHERE ROWNUM =1 ;

        SELECT CASE WHEN :new.c_oid = c_oid THEN :NEW.c_effectivedate ELSE c_effectivedate END INTO position_effdate FROM (SELECT a.c_oid,a.c_effectivedate FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

        SELECT CASE WHEN :new.c_oid = c_oid THEN :new.c_postioncluster ELSE c_postioncluster END INTO position_order FROM (SELECT a.c_oid,a.c_postioncluster FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

        SELECT c_oid INTO position_oid FROM (SELECT a.c_oid FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC) WHERE ROWNUM =1 ;

        --INSERT INTO A_TEMP VALUES('行级别触发器after');

        --INSERT INTO A_TEMP VALUES(position_oid);

       -- INSERT INTO A_TEMP VALUES( to_char(position_effdate,'fmdd month yyyy') );

       -- INSERT INTO A_TEMP VALUES(position_level);

       -- INSERT INTO A_TEMP VALUES(position_order);

        UPDATE tb_inf_employee t SET t.c_positionlevel = position_level,

                                     t.c_positionorder = position_order WHERE t.c_employeeid = :NEW.C_EMPOID;

     END IF;

    COMMIT;

END TB_PER_POSITONLEVEL_TRI;


--测试

SELECT * FROM TB_PER_POSITONLEVEl r WHERE r.c_empoid = '853949' FOR UPDATE --853949

INSERT INTO TB_PER_POSITONLEVEl(c_oid,c_empoid,c_effectivedate)  VALUES('22','853949',to_date('2012-02-10','yyyy-mm-dd'));

DELETE FROM TB_PER_POSITONLEVEl WHERE c_empoid = '853949' AND c_oid = '22'

SELECT t.c_positionlevel,t.c_positionorder FROM tb_inf_employee t WHERE t.c_employeeid = '853949'

UPDATE tb_inf_employee t SET t.c_positionlevel = '11',

                                     t.c_positionorder = '11' WHERE t.c_employeeid = '853949';

SELECT a.c_postioncluster FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = '853949' ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC

SELECT a.c_postionlevel FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = '853949' ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC

SELECT * FROM A_TEMP

DELETE FROM a_temp WHERE 1 = 1  


    结果发现这里的子查询的结果不包括已经修改的记录,就是说before和after在查询关联表的情况下是没有区别的,不知道是怎么个情况,就不包括正在crud的那条记录去掉自治事务,则报错ora:04091,后来又加了一个额外的判断看把查询出来的结果和new、old比较,判断是否修改的是要查的记录。

SELECT CASE WHEN :new.c_oid = c_oid THEN :NEW.c_postionlevel ELSE c_postionlevel END INTO position_level FROM (SELECT a.c_oid, a.c_postionlevel FROM TB_PER_POSITONLEVEl a,tb_inf_employee b WHERE a.c_empoid = b.c_employeeid AND  a.c_empoid = :NEW.c_empoid ORDER BY nvl(a.C_EFFECTIVEDATE,TO_DATE('1900/01/01 00:00:00', 'YYYY/MM/DD HH24:MI:SS') ) DESC,a.c_operatetime DESC)  WHERE ROWNUM =1 ;

    暂时能用了,不过应该写的很不规范。以后在研究吧。

    问题分析:就目前的线索来说,在触发器中不让用关联表使用子查询,mutating table(估计是正在修改的那条记录没有提交呢!!),要是非要这么用,就用自治事务,这时要注意,无论before,after都是不包括正在crud的那条记录,这说明其实触发器的执行过程中after和before其实都没有实际的更新数据库,crud操作和触发器body是在同一个事务中的,after是(crud、触发器body commit的顺序),before是(触发器body、crud commit的顺序)。都是最后一起提交事务,所谓before和after是说在同一个事务中的先后顺序罢了。采用自治事务after应该能达到先crud、在子查询中应该能查到刚才crud的那条记录的,可是实际情况是没有那条记录,这说明oracle在实现触发器的时候有内部的一套机制,需要深入研究才行,目前开发阶段不涉及,以后有时间再研究吧。

分享到:
评论

相关推荐

    Oracle 授权 ORA-00990: 权限缺失或无效

    在Oracle数据库管理中,"ORA-00990: 权限缺失或无效"是一个常见的错误代码,它表示用户尝试执行的操作没有足够的权限。这个错误通常发生在试图访问、修改或者管理数据库对象(如表、视图、索引等)时。在本篇文章中...

    Oracle触发器表发生了变化 触发器不能读它的解决方法(必看)

    出现原因,是因为在更新的的表和读取的表是同一个表。 CREATE or replace TRIGGER T_userupdateT BEFORE update ON T_user REFERENCING OLD AS old NEW AS N_ROW FOR EACH ROW DECLARE U_xtfidemp1 varchar(36);...

    Oracle基于系统级触发器的审计功能

    自Oracle 8i版本开始,Oracle DBMS引入了一种特殊类型的触发器——系统级触发器,它能够针对一系列非DML(数据操纵语言)事件执行特定的操作。本文将详细介绍Oracle系统级触发器的审计功能及其应用场景。 #### 系统...

    ORACLE-DBA面试题

    - PL/SQL:了解存储过程、函数、触发器和游标的编写与应用。 2. **数据库安装与配置**: - 安装过程:描述Oracle软件的安装步骤,如何创建数据库实例。 - 参数文件(init.ora或spfile):理解参数的意义,如何...

    SHOUG文档分享-ORACLE-TTS迁移后ORA3113错误处理-SHOUG成员左翼

    这是一个内部函数,与Oracle进程地址空间的某些部分相关,当函数试图访问未映射到任何对象的地址时就会触发ORA-07445错误。 在对错误进行进一步分析时,使用了ADRCI工具或Support Workbench来打包问题相关的跟踪...

    oracle面试1000例

    - PL/SQL:Oracle的编程语言,用于编写存储过程、函数、触发器。 2. **Oracle架构**: - 实例与数据库的区别:实例是内存结构,数据库是物理存储。 - SGA(System Global Area):包括数据缓冲区、重做日志缓冲...

    oracle-instantclient(64bits)_win

    2. **PL/SQL程序**:编写和执行PL/SQL块,如存储过程、函数和触发器。 3. **应用程序开发**:Oracle Instant Client也适用于开发基于.NET、Java或其他语言的应用程序,这些应用可以通过ODBC、JDBC或OCI接口与Oracle...

    oracle-instantclient11.2-sqlplus-11.2.0.4.0-1.x86_64

    Oracle Instant Client是Oracle公司提供的一款轻量级的数据库连接工具,它允许用户在不安装完整Oracle数据库服务器的情况下,与Oracle数据库进行交互。本压缩包"oracle-instantclient11.2-sqlplus-11.2.0.4.0-1.x86_...

    ORACLE sqlplus命令

    - PL/SQL是Oracle的编程语言,允许编写存储过程、函数、触发器等,增强数据库的交互性和功能。 6. **安全性**: - 用户权限管理,如`GRANT`和`REVOKE`命令,用于分配和回收权限。 - 角色(Role)的使用,可以...

    华为面试题(附答案)Oracle-DBA数据库管理员JAVA程序员架构师必看.doc (2).pdf

    - TRUNCATE更快,不触发表达式和触发器。 - TRUNCATE不保留表的高水平线,删除后表结构重置。 11. 事务理解: - 事务是数据库操作的基本单位,确保数据一致性。 - COMMIT提交事务,ROLLBACK回滚事务。 - DDL...

    plsql不能连接linux下oracle问题ORA-12514.doc

    PL/SQL作为Oracle的过程语言,能够在Oracle数据库中执行存储过程、函数和触发器等。然而,在Linux环境下,PL/SQL可能无法连接到Oracle数据库,出现ORA-12514错误。本文档旨在解决这个问题,提供了详细的解决方案。 ...

    Oracle 11g 从入门到精通

    Oracle 11g是Oracle公司推出的数据库管理系统,它在企业级数据存储、管理和分析方面具有广泛的应用。本教程“Oracle 11g 从入门到精通”旨在帮助初学者掌握Oracle 11g的核心概念和技术,逐步提升为熟练的数据库管理...

    oracle DBA两日速成手册1

    Oracle DBA,即Oracle数据库管理员,是管理和维护Oracle数据库系统的关键角色。"Oracle DBA两日速成手册1"提供了一个快速学习Oracle DBA基础知识的框架,尤其适合初学者或需要快速掌握Oracle DBA技能的人士。以下是...

    oracle高级语法(事物、函数、存储过程、触发器、异常)[参照].pdf

    Oracle 高级语法是指在 Oracle 数据库管理系统中使用的高级语法结构,包括事务、函数、存储过程、触发器、异常等。这些语法结构是 Oracle 数据库开发和管理的核心内容,对于数据库开发者和管理员来说是必备的知识。 ...

    oracle 11i 中文帮助手册

    Oracle 11i 是 Oracle 公司在2000年代初期发布的企业级数据库管理系统,它为各种规模的企业提供了全面的数据管理和分析功能。这个中文帮助手册涵盖了 Oracle 11i 的核心概念、安装配置、数据库管理、SQL 语言、PL/...

    Oracle Instant Client_12_1 Downloads

    Oracle Instant Client是Oracle公司提供的一款轻量级的数据库连接工具,它允许用户在不安装完整Oracle数据库服务器的情况下,实现对Oracle数据库的访问和查询。在本文中,我们将深入探讨Oracle Instant Client的功能...

    oracle10g学习课件

    - PL/SQL:Oracle的面向过程的编程语言,用于编写存储过程、触发器、函数等数据库对象。 5. **安全性管理** - 用户与角色:创建用户,分配权限,理解角色的概念,以实现安全的多用户访问。 - 权限与系统权限:...

    plsql-oracle-instantclient-x86-64-11.2.0.1.0

    1. "plsql":这是对PL/SQL的简称,Oracle数据库的一种过程式语言,用于编写存储过程、函数、触发器等。 2. "x86-64":表明该版本是为64位(AMD64或Intel 64)架构的计算机设计的。 3. "11.2.0.1.0":这是Oracle...

    oracle PPT教程

    Oracle数据库是全球广泛使用的大型关系型数据库管理系统,它在企业级数据存储、管理和处理方面扮演着重要角色。本"Oracle PPT教程"旨在提供全面的Oracle语言基础和实践技巧,帮助学习者掌握Oracle数据库的核心概念及...

    sqldeveloper 连接oracle的另外一种工具

    作为一款轻量级的替代品,它在许多方面与PL/SQL Developer相似,但通常对硬件需求更低,例如只需要一个32位的Java Development Kit (JDK) 就能运行,这对于那些系统资源有限或者不想安装完整版Oracle客户端的用户来...

Global site tag (gtag.js) - Google Analytics