PL/SQL 异常

        程序执行过程中的错误情况是一个例外(异常)。PL/SQL支持程序员在程序中使用异常块捕获这些发生错误的情况,并针对这些错误情况采取适当的措施。

        PL/SQL中有两种异常:

  • 系统定义的异常
  • 用户定义的异常

预定义的异常

        PL/SQL提供了许多预定义的异常,这些异常在程序违反任何数据库规则时执行。例如,当SELECT INTO语句不返回任何行时,会引发预定义的异常NO_DATA_FOUND。下表列出了一些重要的预定义异常情况:

异常描述
ACCESS_INTO_NULL当一个空对象被自动分配一个值时会引发它。
CASE_NOT_FOUND当没有选择CASE语句的WHEN子句中的任何选项时,会引发这个错误,并且没有ELSE子句。
COLLECTION_IS_NULL当程序尝试将EXISTS以外的集合方法应用于未初始化的嵌套表或varray时,或程序尝试将值分配给未初始化的嵌套表或varray的元素时,会引发此问题。
DUP_VAL_ON_INDEX当尝试将重复值存储在具有唯一索引的列中时引发此错误。
INVALID_CURSOR当尝试进行不允许的游标操作(例如关闭未打开的游标)时会引发此错误。
INVALID_NUMBER当字符串转换为数字时失败,因为字符串不代表有效的数字。
LOGIN_DENIED当程序尝试使用无效的用户名或密码登录到数据库时引发。
NO_DATA_FOUNDSELECT INTO语句不返回任何行时会引发它。
NOT_LOGGED_ON当数据库调用没有连接到数据库时引发。
PROGRAM_ERROR当PL/SQL遇到内部问题时会引发。
ROWTYPE_MISMATCH当游标在具有不兼容数据类型的变量中获取值时引发。
SELF_IS_NULL当调用成员方法时引发,但对象类型的实例未初始化。
STORAGE_ERROR当PL/SQL用尽内存或内存已损坏时引发。
TOO_MANY_ROWSSELECT INTO语句返回多行时引发。
VALUE_ERROR当发生算术,转换,截断或者sizeconstraint错误时引发。
ZERO_DIVIDE当尝试将数字除以零时引发。

异常处理的语法

        在异常块中列举尽可能多的异常并且指定处理方式。默认的异常将使用WHEN...THEN处理,异常处理的一般语法如下:

DECLARE

        <declarations section>

BEGIN

        <executable command(s)>

EXCEPTION

        <exception handling goes here >

        WHEN exception1 THEN

                exception1-handling-statements

        WHEN exception2 THEN

                exception2-handling-statements

        WHEN exception3 THEN

                exception3-handling-statements

                ........

        WHEN others THEN

                exception3-handling-statements

END;

下面是一个未找到数据记录时的异常处理:

DECLARE
   c_id customers.id%type := 100;
   c_name  customers.name%type;
   c_addr customers.address%type;
BEGIN
   SELECT name, address INTO c_name, c_addr
   FROM customers
   WHERE id = c_id; 
   DBMS_OUTPUT.PUT_LINE ('姓名: '||  c_name);
   DBMS_OUTPUT.PUT_LINE ('地址: ' || c_addr);
EXCEPTION
   WHEN no_data_found THEN
      dbms_output.put_line('没有找到符合条件的客户信息!');
   WHEN others THEN
      dbms_output.put_line('Error!');
END;
/

引发异常

        只要发生内部数据库错误,数据库服务器就会自动产生(引发)异常。此外程序员也可以使用命令RAISE明确地引发异常。以下是引发异常的简单语法:

DECLARE

        exception_name EXCEPTION;

BEGIN

        IF condition THEN

                RAISE exception_name;

        END IF;

EXCEPTION

        WHEN exception_name THEN

                statement;

END;

可以使用上述语法来引发Oracle标准异常或任何用户定义的异常。 

用户定义的异常

        PL/SQL允许根据程序的需要定义自己的异常。 用户定义的异常必须声明,然后使用RAISE语句或过程DBMS_STANDARD.RAISE_APPLICATION_ERROR显式地引发。

DECLARE
   C_ID CUSTOMERS.ID%TYPE := &CC_ID;
   C_NAME  CUSTOMERS.NAME%TYPE;
   C_ADDR CUSTOMERS.ADDRESS%TYPE;

   -- USER DEFINED EXCEPTION
   EX_INVALID_ID EXCEPTION;
BEGIN 
   IF C_ID <= 0 THEN
      RAISE EX_INVALID_ID;
   ELSE
      SELECT NAME, ADDRESS INTO C_NAME, C_ADDR
      FROM CUSTOMERS
      WHERE ID = C_ID;
      DBMS_OUTPUT.PUT_LINE ('姓名: '||  C_NAME);
      DBMS_OUTPUT.PUT_LINE ('地址: ' || C_ADDR);
   END IF;
EXCEPTION
   WHEN EX_INVALID_ID THEN
      DBMS_OUTPUT.PUT_LINE('编号ID必须要大于0!');
   WHEN NO_DATA_FOUND THEN
      DBMS_OUTPUT.PUT_LINE('未找到指定ID的客户信息!');
   WHEN OTHERS THEN
      DBMS_OUTPUT.PUT_LINE('ERROR!');
END;
/
  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值