当前位置:文档之家› PLSQL基本语法归纳

PLSQL基本语法归纳

======================PLSQL=========================


PL/SQL使用“--”注释单行和“/**/”注释多行


一、基本类型
1、PL/SQL块

【PL/SQL块结构】
声明部分(DECLARE):声明变量、常量、游标、类型,以及局部的存储过程和函数
执行部分(BEGIN---END):执行语句,操作数据库
异常处理(EXCEPTION):对异常和错误进行处理
-------------------------------------
<> //有名块标号
[DECLARE]
--declare;
BEGIN
--execute;
[EXCEPTION]
--exception;
END [block_name]
-------------------------------------

【块分类】:
无名块:动态构造,只能执行一次
有名块:加了标号的无名块
子程序:包括存储在数据库中的存储过程,函数和包,可以随时调用
-------------------------------------
CREATE OR REPLACE PROCEDURE block_name AS
--declare;
BEGIN
--execute;
END [block_name]
-------------------------------------
触发器:存储在数据库中的块,一旦相关事件被触发则执行本块
-------------------------------------
CREATE OR REPLACE TRIGGER block_name
--when and where
BEGIN
--execute;
END [block_name]
-------------------------------------


2、变量
【标识符】
不带双引号的标识符:以字母开头,可以为字母,数字和特殊字符($、#、_)组成,并且长度不超过30的字符串(不区分大小写)
带双引号的标识符:同不带双引号的标识符,但可以区分大小写和可包含空格等其他特殊字符。

【数据类型】
a.标量类型:
NUMERIC用于存放整数,实数和浮点数
1)BINARY_INTEGER:存储带符号的整数(-2147483647~2147483647),对应的派生类型:
NATURAL:存储非负的整数
NATURALN:存储非负的整数,不能为空
POSITIVE:存储正整数
POSITIVEN:存储正整数,不能为空
SIGNTYYE:存储-1,0和1
2)NUMBER:可以存储定点数,整形数和浮点数(1.0E-130~9.99E125),对应的派生类:
定点数:DEC、DECIMAL、NUMERIC最大精度为38
type(precision,scale),其中precision表示精度(1~38),scale(-84~127)表示标度,标度指定从什么位置进行四舍五入,当scale>0时表示从小数点右边小数部分第scale位开始,如果scale<0时从小数点左边整数部分第scale位开始。
浮点数:DOUBLE PRECISION、FLOAT最大精

度为38,REAL最大精度为18
type,精度为38或则18的浮点数,没有精度的概念
整形数:INTEGER、INT、SMALLINT,最大精度为38
type(precision),只需指定精度即可
3)PLS_INTEGER:
存储带符号的整数范围同BINARY_INTEGER(-2147483647~2147483647),速度比NUMBER和BINARY_INTEGER块,但是PLS_INTEGER会出现溢出错误,而BINARY_INTEGER在NUMBER类型之间赋值时,即使有溢出也不会出现溢出错误
CHARACTER用于存放字符串,对应的派生类型有:
1)CHAR:用于存放固定长度的字符数据
CHAR[(length)],1<=length<=32767,length的默认长度为1。其实数据库最大的CHAR类型的列最大存储2000个字符,因此不能直接把大于2000字符的字符串直接插入到数据库列中,但可以插入到VARCHAR2或LONG类型的列中。
2)NCHAR:用于存放固定长度的NLS字符数据。其他同CHAR,但NCHAR和CHAR之间的数据不能直接交换
3)VARCHAR2:用于存放变长字符类型。
VARCHAR2(length),length取值范围同CHAR,但数据的内部表示取决于当前数据库的字符集。数据库中VARCHAR2类型的列的最大存储为4000个字节,因此大于4000的可以存储到LONG类型的列中。
4)NVARCHAR2:用于存放可变长度的NLS字符数据。其他同VARCHAR2,但VARCHAR2和VARCHAR2之间的数据不嫩直接交换
5)LONG:用于存储可变长字符数据,最大长度为32760,但数据库中LONG类型的列中可以存放2G的数据。
RAW用于存储二进制数据,对应的派生类型有:
1)RAW:存放固定长度的二进制数据。
RAW(length),1<=length<=32767,数据库中RAW列最大长度为2000,因此不能直接把大于2000字节的值插入数据库列中,可以插入LONG RAW列
2)LONG RAW:最大长度为32760,数据库中的LONG RAW列最大长度为2G,因此不能直接从数据库中读取数据存放于PL/SQL的LONG RAW类型变量中
ROWID用于存储行标识,每个数据表都有一个ROWID伪列,是固定长度的十六进制的字符串,表示一条记录的存储地址。
DATE用于存储长度固定的日期和时间值,日期范围为公元前4712.1.1到公园后4712.12.31。日期的缺省值为当月的第一天,时间的缺省值为午夜12:00
可以使用TO_DATE和TO_CHAR在CHARACTER和DATE之间转换
BOOLEAN用于存储逻辑值,TURE,FALSE和NULL。
NULL表示一个错误的,不合适或者不确定的值。BOOLEAN类型在数据库中不存在,只能用在PL/SQL中做逻辑运算。
TRUSTED,MLSLABEL类型的变量被用在Trusted Oracle中存储变

长的二进制标签
标量类型之间的转换:
1)强制转换:通过使用函数完成不同类型之间的转换
TO_CHAR:将NUMERIC和DATE类型转换成VARCHAR2类型
TO_DATE:将CHARACTER类型转换成DATE类型
TO_NUMBER:将CHARACTER类型转换成NUMBER类型
RAWTOHEX:将RAW类型转换成十六进制数值
HEXTORAW:将CHARACTER类型描述的十六进制转换成二进制数
CHARTOROWID:将CHARACTER类型描述的ROWID转换成二进制数
ROWIDTOCHAR:将二进制的ROWID转换成18个字符的行标识符
2)自动转换:某些数据类型中间可以进行自动转换

b.复合类型:
复合类型是用户自定义的类型,在使用之前必须定义好。
1)记录:
-------------------------------------
TYPE record_type IS RECORD(
field1 type1[NOT NULL] [:=value1]
field2 type2[NOT NULL] [:=value2]
...
fieldn typen[NOT NULL] [:=valuen]
)
-------------------------------------
定义了记录后,可以当作基本类型使用,而且这里可以通过简单的%ROWTYPE定义一个与表字段一样的变量,如v_Record table%ROWTYPE。
2)集合:(类似于数组)
index_by表:不能直接存储在数据库中
-------------------------------------
TYPE table_name IS TABLE OF type [NOT NULL] INDEX BY BINARY_INTERGER
-------------------------------------
嵌套表:可以作为列存储在数据库中,但实际上数据库是通过另一张表存储嵌套表这列,其不能保证取得的元素的顺序;属于离线存储,适合大型数据集合。
-------------------------------------
TYPE table_name IS TABLE OF type [NOT NULL]
-------------------------------------
VARRAY:可以作为列存储在数据库中,于表中的其他数据存放在同一张表中,并顺序保存;属于在线存储,适合小型数据集合。
-------------------------------------
TYPE table_name IS [VARRAY|VARYING ARRAY](max_size) OF type [NOT NULL]
-------------------------------------
index_by表、嵌套表和VARRAY都有以下表属性(通过table.attribute获取属性值):
COUNT:PL/SQL表中元素个数
DELETE:删除PL/SQL表中的元素
DELETE删除全部
DELETE(i)删除第i个元素
DELE

TE(i,j)删除第i到j个元素
EXISTS(i):索引号为i的元素是否存在
FIRST:返回PL/SQL表中第一个元素的索引
LAST:返回PL/SQL表中最后一个元素的索引
NEXT(i):返回PL/SQL表中索引为i的后一个元素的索引
PRIOR(i):返回PL/SQL表中索引为i的前一个元素的索引

c.引用类型:
引用类型类似于C中的指针,用于存储指向存储空间的指针,包括游标和对象引用类型

d.LOB类型:
用于存储大对象。可以存储不超过4G的二进制数据或者字符数据,通过DBMS_LOB包来操作LOB类型

e.用户自定义类型
系统有预定义的子类,用户可以在PL/SQL块的定义部分定义自己的子类型
SUBTYPE subtype_name IS base_type
base_type是可以是基本数据类型、%TYPE和%ROWTYPE
base_type不能直接指定变量的长度,精和标度,及不能定义为SUBTYPE my_type IS NUMBER(4),但是可以通过一下方式达到效果
-------------------------------------
DECLARE
v_temp NUMBER(4);
SUBTYPE my_type IS v_temp%TYPE;
my_type my_Num;
-------------------------------------

【数据】
a.字符型数据
字符型数据是指包含在单引号('')中的字符串。
b.数值型数据
可以赋值个NUMBER类型的数据,分为整数和实数。
整数:没有小数点的完整数值
实数:带有小数点的数值
c.布尔型数据
用于条件判断的值,有TRUE,FALSE和NULL三个值。

【变量申明】
声明变量时,为变量分配存储空间,指定数据类型和存储空间的名称。
a.声明变量的语法
variable_name [CONSTANT] type [NOT NULL] [:=value]
b.变量的作用域和可视域
作用域:指变量在程序中的有效范围。PL/SQL变量,其作用域是在变量被声明开始,到其所在块结束。
可视域:是指在变量前不加以限定就能够直接访问该变量的那一段程序,变量的可视域总是在作用域之内。
-------------------------------------
<>
DECLARE
v_num NUMBER(3,4);
BEGIN
v_num := 1;
DECLARE
v_num CHAR(10);
BEGIN
v_num := 'charValue';
l_father.v_num = 45;
END;
END;
-------------------------------------

【赋值语句】
variable := expression;


【表达式】
**:求幂
+、-:正负号
*、/、+、-:算数运算符
||:连接多个字符串
=、!=、<、>、<=、>=、IS NULL、LIKE、BETWEEN AND、IN:比较
AND:逻辑与
OR:逻辑或
NOT:逻辑非

【注释】
单行注释:--
多行注释:/**/



二、控制语句
【选择控制语句】
a.IF...THEN
-------------------------------------
IF 条件 THEN
语句;
END IF;
-------------------------------------

b.IF...THEN...ELSE
-------------------------------------
IF 条件 THEN
语句;
ELSE
语句;
END IF;
-------------------------------------

c.IF...THEN...ELSIF
-------------------------------------
IF 条件 THEN
语句;
ELSIF 条件 THEN
语句;
[ELSE
语句;]
END IF;
-------------------------------------

【循环控制语句】
a.LOOP
-------------------------------------
LOOP
语句;
END LOOP;
-------------------------------------
可以用EXIT和EXIT WHEN退出循环,也可以使用标号<<>>使程序跳转到指定位置。

b.WHILE...LOOP
-------------------------------------
WHILE 条件 LOOP
语句;
END LOOP;
-------------------------------------

c.FOR...LOOP
-------------------------------------
FOR 循环变量 IN [REVERSE] 初始值..结束值 LOOP
语句;
END LOOP;
-------------------------------------
每执行一次,循环变量自动加1,如果使用REVERSE则循环变量自动减1,包括初始值和结束值

【顺序控制语句】
a.GOTO
无条件的跳转到某个标号<>

b.NULL
用于明显的指定一个什么也不执行的语句,相当于占位符。



三、游标
环境区域是用来处理SQL语句的一个Oracle存储区域。游标是指向它的指针或句柄,PL/SQL可以通过这个游标控制这个环境区域中被处理的语句。
【显式游标】
在块定义部分、包或者子程序中申明,使用CURSOR...IS命令定义的游标,可以对查询语句返回的多条记录进行处理。
游标声明后可以通过打开游标,推进游标,关闭游标操作游标。
a.申明显式游标
-------------------------------------
CURSOR cursor_nam

e[(parameter,parameter,...)]
[RETURN return_type] IS select_statement;
-------------------------------------
其中parameter是parameter_name [IN] datatype[{:=|DEFAULT} expr]。

b.打开游标
打开游标做的处理是先查找绑定在游标中的变量,然后安装该变量的值确定查询结果集。
-------------------------------------
OPEN cursor_name[(parameter,parameter,...)];
-------------------------------------

c.推进游标
-------------------------------------
FETCH cursor_name INTO list_of_variables;

FETCH cursor_name INTO PL/SQL_record;
-------------------------------------
其中list_of_variables是已什么的变量列表,PL/SQL_record是已经定义好的PL/SQL记录。

d.关闭游标
-------------------------------------
CLOSE cursor_name;
-------------------------------------

【游标属性】
游标有四个属性,分别为%FOUND、%NOTFOUNT、%ISOPEN、%ROWCOUNT,这些属性只能用在过程性语句中,不能用在SQL语句中
a.%FOUND
如果FETCH语句成功返回一行,则该属性返回TRUE,反之返回FALSE

b.%NOTFOUND
与%FOUND相反

c.%ISOPEN
返回游标是否打开

d.%ROWCOUNT
返回游标推进的行数

【显式游标的推进循环】
可以使用循环(LOOP...END LOOP和WHILE...LOOP)和游标属性结合实现游标数据的提取,但必须对游标进行OPEN、FETCH、CLOSE来显式控制游标。
这里可以使用FOR...LOOP语句实现游标的自动打开,推进,关闭操作。
-------------------------------------
DECLARE
--定义游标和变量
BEGIN
--循环开始前自动打开游标
FOR 变量 IN 游标 LOOP
--隐含的执行一次FETCH语句,读取到变量中
语句;
--隐含的检测%NOTFOUND被检测
END LOOP
--循环结束后自动关闭游标
END;
-------------------------------------

【隐式游标处理】
隐式游标也叫SQL游标,它不能通过专门的命令打开或关闭游标。SQL游标用于处理INSERT、UPDATE、DELETE以及返回一行的SELECT...INTO语句。
隐式游标的属性也有四种,通过SQL%attribute引用,但跟显式游标的属性有些不同:
%FOUND:当执行DML语句并成功返回一行后,结果为TRUE。如果SELECT...INTO返回了多行时,会产生TOO_MANY_ROWS异常,并把控制权交到异常处理部分,SQL%FOUND并不返回TRUE,如果返回0行,会产生NO_DATA_FOUND异常,

并且属性值为FALSE。
%NOTFOUND:跟%FOUND相反
%ISOPEN:由于在执行DML后,Oracle会自动关闭SQL游标,因此次属性值永远为FALSE
%ROWCOUNT:返回得到的行数。如果SELECT...INTO返回了多行,则产生TOO_MANY_ROWS异常,并把控制权交到异常处理部分。

【游标变量】
游标变量是一个引用的变量,类似C中的指针,因此游标变量在运行时可以动态的指定不同的查询语句。
a.游标变量的声明:
-------------------------------------
TYPE type_name IS REF CURSOR RETURN return_type;
-------------------------------------

b.打开游标变量:
-------------------------------------
OPEN cursor_variable FOR select_statement;
-------------------------------------

c.推进游标变量:
同静态游标推进方法一样

d.关闭游标变量:
同静态游标推进方法一样



四、存储过程和函数
【创建存储过程】
a.语法
-------------------------------------
CREATE [OR REPLACE] PROCEDURE [schema.]procedure_name
[(argument [{IN|OUT|IN OUT}] datatype [,...])]
{IS | AS}
PL/QSL_body;
-------------------------------------
参数:
IN:只读的输入参数
OUT:只写的输出参数
IN OUT:读写参数
处理部分:
包括定义部分,可执行部分以及异常处理部分。

b.存储过程的参数
参数数据类型:
存储过程的参数在使用CHAR,VARCHAR2不能指定其形参的长度,在使用NUMBER时不能指定形参的精度和标度。这些长度以及精度和标度在存储过程调用时都由实参来决定。如果通过%TYPE定义,就有指定类型的长度或者精度和标度。
参数传值方式:
位置表示法:通过位置来传送参数,在调用时,实参的传入顺序必须与形参定义时的顺序相同
名称表示法:通过名称来决定传入参数,调用时通过(形参=>实参)的方式传入参数
位置表示法和名称表示法可以混用,但当某个位置使用名称表示法后,其后面的所有参数都必须使用名称表示法
参数缺省值:
可以使用:=或者DEFAULT为参数定义缺省值,可以在调用的时候不为其传递实参。


【创建函数】
a.语法
-------------------------------------
CREATE [OR REPLACE] FUNCTION schema.function
[(argument [{IN|OUT|IN OUT}] datatype [,....])]
RETURN return_datatype {IS | AS}

PL/SQL_body;
-------------------------------------
函数必须有一个返回值

b.函数和存储过程
都可以通过OUT参数返回多个值
代码都有定义部分,可执行部分和异常处理部分
都可以使用缺省值
都可以使用位置表示法和名称表示法传递参数

【删除过程与函数】
删除存储过程:
-------------------------------------
DROP PROCEDURE procedure;
-------------------------------------
删除函数:
-------------------------------------
DROP FUNCTION function;
-------------------------------------

【库存子程序和局部子程序】
库存子程序:
存储在数据库中的子程序。
局部子程序:
在块的定义部分创建的子程序。局部子程序在创建时,不需要CREATE [OR REPLACE]声明,直接FUNCTION function[(parameter,...)] RETURN return_type IS body即可。



五、包
包可将一些有联系的对象放在其内部,包括存储过程,函数,游标,自定义的类型和变量。包头中定义了存储过程和函数,则必须定义包体以实现这些存储过程和函数,否则可以不用定义包体。
【包的定义】
一个包又两部分组成:包头和包体。
a.定义包头
-------------------------------------
CREATE [OR REPLACE] PACKAGE [schema.]package
{IS|AS}
PL/SQL_package
END;
-------------------------------------
其中PL/SQL_package可以是存储过程,函数,变量,类型,异常以及游标的定义。
包头中仅定义存储过程或函数的名称以及它们的参数,而它们的执行代码将在包体中定义。

b.定义包体
包体是数据字典的对象,只有在包头成功编译后包体才能被编译。并且包体只定义已经包含在对应包头中已经定义的子程序代码。
-------------------------------------
CREATE [OR REPLAE] PACKAGE BODY [schema.]package
{IS|AS}
PL/SQL_body;
-------------------------------------

c.包的初始化
可以在包体中作一些初始化操作:
-------------------------------------
CREATE [OR REPLACE] PACKAG BODY package {IS|AS}
define_partment;
BEGIN
initializetion_code;
END;
-------------------------------------

【包的使用】
a.包中对象的引用
包名.对象名

b.重载包的子程序
包中的存储过

程和函数都可以被重载,及相同名称不同参数的存储过程或者函数。
规则:
当仅仅参数名不同或者是模式(IN、OUT、IN OUT)不同时,不能重载子程序。
不能对仅有返回类型的函数进行重载。
重载函数的参数必须是数据类型的不同或是其类型之间不可自动转换。

【在SQL语句中使用的函数】
通常在SQL中不能调用PS/SQL定义的函数,因此为函数定义了以下约束:
WNDS(Writes no database state):在函数内不能使用DML语句修改数据库中的表
RNDS(Reads no database state):在函数内不能那个通过SELECT语句来读取数据库中的表
WNPS(Writes no package state):在函数内不能修改包变量
RNPS(Reads no package state):在函数内不能读取包变量
a.满足以下约束的PL/SQL函数时可以被SQL语句调用
当函数满足WNPS时,能被SQL语句调用
当函数满足RNPS和WNPS约束时,这个函数能被远程或并行调用
在SELECT、VALULES或SET子句中调用的函数可以没有WNPS约束,但其它子句中就必须满足WNPS约束
一个函数所调用的子程序与该函数的约束级别相同
在含有CREATE TABLE或者ALTER TABLE命令的CHECK子句中,不能调用存储在数据库中的PL/SQL函数,因为这些语句中的定义不能改变

b.用户自定义的函数必须符合如下约束才能被SQL语句调用,也可用于内嵌函数:
函数必须单独的作为包的一部分存储在数据库中,不能作为块的一部分
函数只能定义IN参数,不能那个定义IN OUT或者OUT参数
形参类型必须是数据库中的类型,不能是PL/SQL中的数据类型
函数返回的数据类型也必须是数据库中的数据类型

c.可以通过RESTRICT_REFERENCES编译指令来指定包函数的约束:
-------------------------------------
PRAGMA RESTRICT_REFERENCES(function_name,
WNDS[,WNPS][,RNDS][,RNPS]);
-------------------------------------
只需要在包头中定义好了函数后,通过这条编译指令指定其约束。这里WNDS是必选的。
在使用RESTRICT_REFERENCES时应注意的几点:
PL/SQL编译程序根据编译指令来确定包函数的基本约束,从而确定这个包函数能不能在SQL语句中使用。
包初始化部分的代码同样也可以有基本的约束。包的基本约束也用RESTRICT_REFERENCE来指定,但报名为参数而不是以函数数名为参数。
RESTRICT_REFERENCE可以在包中函数定义后的任何位置出现,但它只能约束一个函数的定义。

d.如果函数中用到

了DDMS_OUTPUT、DBMS_PIPE、DBMS_ALTER、DBMS_SQL、UTL_FILE等系统包,则该函数不能用在SQL语句中调用。

【系统提供的包DBMS_OUTPUT】
DBMS_OUTPUT包提供了一下存储过程:
PUT(param):输出
PUT_LINE(param):输入并且换行
NEW_LINE:直接输出换行
GET_LINE(line,status):输入,用于返回一个字符串和一个用来标识成功的状态,如果成功返回0,否则为1
GET_LINES(line,status):返回一个PL/SQL表,该表的定义为(TYPE CHARARR IS TABLE OF VARCHAR2(255) INDEX NY BINARY_INTEGER)
ENABLE(buffer_size):控制缓冲区的大小,默认为20000,最大为1000000
DISABLE:清除缓冲区的类容,并收回缓冲区,再次调用PUT或PUT_LINE后,不会在存入缓冲区



六、异常处理
PL/SQL中出现的警告或错误叫做异常。
【预定义异常】
系统已经定义好的异常,可以直接使用。
常见的系统预定义异常:
DUP_VAL_ON_INDEX:违反唯一性约束
TIMEOUT_ON_RESOURCE:等待资源超时
TRANSACTION_BACKED_OUT:由于死锁使得事务回退
INVALID_CURSOR:执行了非法的游标操作
NOT_LOGGED_ON:没有连接到Oracle
LOGIN_DENIED:错误的用户名或口令
NO_DATA_FOUND:SELECT...INTO没有数据返回,或试图引用一个还没被赋值的PL/SQL表元素
TOO_MANY_ROWS:一条SELECT...INTO语句查询到多行结果
ZERO_DIVIDE:被0除
INVALID_NUMBER:未能将SQL语句中的字符串转换成数字
STORAGE_ERROR:PL/SQL运行时内存溢出
PROGRAM_ERROR:内部的PL/SQL错误,这属于系统软件的问题
VALUE_ERROR:在过程性语句中出现转换、截断、算数错误而产生的异常
ROWTYPE_MISMATCH:一个主游标变量和PL/SQL游标变量的类型不匹配
CURSOR_ALREADY_OPEN:试图打开一个已经打开的游标
ACCESS_INTO_NULL:试图给一个NULL对象的属性赋值
COLLECTION_IS_NULL:试图对一个NULL值的PL/SQL表或变长的数组进行除EXISTS意外的操作
SUBSCRIPT_OUTSIDE_LIMIT:引用的嵌套表或变长数组索引超出了其申明范围
SUBSCRIPT_BEYOND_COUNT:引用的嵌套表或变长数组索引超出了其什么范围


【用户自定义异常】
a.异常的声明
-------------------------------------
exception_name EXECPTION;
-------------------------------------
预定义异常对应了部分Oracle错误,用户可以为Oracle的其他错误声明自定义错误,及通过EXECEPTION_INIT编译指令:
-------------------------------------
PRAGMA EXECEPTION_INIT(exception_name,Oracle_error_number);
-------------------------

------------
exeception_name是预先自定义的异常名,而Oracle_error_number是系统Oracle错误号。这条命令必须写在块的定义部分。
通过EXECEPTION_INIT,一个自定义异常只能和一个Oracle错误代码相连,一旦系统参数这种错误的异常,就会自动识别并跳转到用户的处理部分,在异常处理语句中SQLCODE和SQLERRM将返回本次异常的代码和消息文本。

b.异常的产生
当与预定义异常对应的错误出现时,则该预定义异常就会自动产生。而一个用户自定义异常通常由RAISE语句产生(有EXCEPTION_INIT编译指令申明的用户自定义异常也是根据Oracle错误的出现自动产生)。如果需呀,预定义异常也可以由RAISE语句产生。
-------------------------------------
RAISE exception_name;
-------------------------------------
通常用户自定义异常是在什么后才能产生,但如果使用RAISE_APPLICATION_ERROR函数就可以直接产生异常,并能为异常定义用户自己指定的错误消息。而且执行RAISE_APPLICATION_ERROR函数后,控制权会转换到块外的调用环境。
-------------------------------------
RAISE_APPLICATION_ERROR(error_number,error_message,[keep_errors]);
-------------------------------------
其中error_number是一个错误号,在-20000到-20999之间,
error_message是与该错误相连的错误消息文本,不能超过512字节;
keep_errors是BOOLEAN值,可选参数,如果为TRUE则这个错误将加在已产生的错误列表之后,如果为FALSE这个错误将代替当前错误列表。

【异常处理】
-------------------------------------
EXCEPTION
WHEN exception_name THEN
sequence_of_satements1;
WHEN exception_name THEN
sequence_of_satements2;
...
WHEN OTHERS THEN
sequence_of_satementsn;
END;
-------------------------------------
如果一个处理语句对应多个异常处理,只需要在WHEN子句中通过OR分割多个异常名。
如果在该块中没有处理产生的异常,则这个异常会返回到调用它的程序,可能会导致调用它的程序出错,如果在存储过程中出现异常,则存储过程的OUT参数将得不到返回值。
a.处理可执行部分产生的异常
可执行部分产生了异常,如果在该块中实现了此异常的处理,则成功返回,如果未实现此异常的处理,则此异常将会被传递到该块外的调用环境中。

b.处理定义部分产生的异常
定义部分产生了异常,无

论该块是否实现了对该异常的处理,这个异常都会传递到该块外的调用程序中,由调用程序处理。

c.处理异常处理部分产生的异常
异常处理部分产生了异常,与定义部分产生的异常处理相同,传递到该块外的调用程序中处理。

d.SQLCODE和SQLERRM函数
在异常处理中,特别是OTHERS处理中,可以通过SQLCODE获取错误代码以及通过SQLERRM获取错误信息:
异常种类 SQLCODE SQLERRM
Oracle错误对应的异常 负数 Oracle错误
NO_DATA_FOUNE +100 No data found
用户自定义异常 +1 User-Defined Exception
没有产生异常 0 ORA-0000:normal,successful completion
如果自定义异常通过EXCEPTION_INIT预编译命令与Oracle错误相连,则SQLCODE和SQLERRM产生的信息是绑定额相关Oracle错误信息,而不是+1。
调用SQLERRM时可以带一个数字参数,返回值是与这个数字参数相关的信息文本,如SQLERRM(0)的返回值是"ORA-0000:normal,successful completion"。

相关主题
文本预览
相关文档 最新文档