先来看一个简单的存储过程
create or replace procedure proc1(
para1 varchar2,
para2 out varchar2,
para3 in out varchar2
) as
v_name varchar2(20);
begin
v_name :='zhanghaiwei';
para3 := v_name;
dbms_output.put_line('para3:'||para3);
end;
其构成:
- 创建语句:create or replace procedure 存储过程名
如果没有or replace语句,则仅仅是新建一个存储过程。如果系统存在该存储过程,则会报错。Create or replace procedure 如果系统中没有此存储过程就新建一个,如果系统中有此存储过程则把原来删除掉,重新创建一个存储过程。
存储过程名定义:包裹存储过程名和参数列表(参数名和参数类型),参数名不能重复,参数传递方式:IN,OUT,IN OUT:
IN表示输入参数,按值传递方式。如果存储过程的参数没有指定存参数传递类型,默认为IN ;
OUT表示输出参数,可以理解为按引用传递方式,可以作为存储过程的输出结果,供外部调用者使用。需要注意,当一个参数被指定为OUT类型时,就算在调用存储过程之前对该参数进行了赋值,在存储过程中该参数的值仍然是null;
IN OUT既可以作为输入参数,也可作为输出参数;
参数的数据类型只需要指明类型名即可,不需要指定宽度,参数的宽度由外部调用者决定。
- 变量声明块
紧跟着as(is)关键字,或者用declare关键字,用于声明变量,变量声明块用于声明该存储过程需要用到的变量,他的作用域为该存储过程,另外这里声明的变量必须指定宽度,遵循PL/SQL的变量声明规范。
- 过程语句块
从begin 关键字开始为过程的语句块。存储过程的具体逻辑在这里来实现。
- 异常处理块
关键字为exception ,为处理语句产生的异常。该部分为可选
- 结束块
由end关键字结果
另附:
我们无法在存储过程的定义中指定存储参数的宽度,也就导致了我们无法在存储过程中控制传入变量的宽度,这个宽度是完全由外部传入是决定的。
create or replace procedure proc2(
para1 varchar2,
para2 out varchar2,
para3 in out varchar2
) as
v_name varchar2(2);
begin
para2 :='aaaaaaaaaaaaaaaaaaaa';
end;
--调用proc2
var p1 varchar2(1);
var p2 varchar2(1);
var p3 varchar2(1);
exec :p2 := 'a';
exec proc1(:p1,:p2,:p3);
在该过程中,p_para2被赋予了20个字符a.
而在外部的调用过程中,p2这个参数仅仅被定义为varchar2(1).
而把p2作为参数调用这个过程,却并没有报错。而且它的真实值就是20个a
执行这个过程,仍然正确执行。
可见,对于IN参数,其宽度是由外部决定。
对于OUT 和IN OUT 参数,其宽度是由存储过程内部决定。
因此,在写存储过程时,对参数的宽度进行说明是非常有必要的,最明智的方法就是参数的数据类型使用%type。这样双方就达成了一致。
参数默认值
create or replace procedure procdefault(
p1 varchar2,
p2 varchar2 default 'mark'
) as
begin
dbms_output.put_line(p2);
end;
可以通过default 关键字为存储过程的参数指定默认值。在对存储过程调用时,就可以省略默认值。
需要注意的是:默认值仅仅支持IN传输类型的参数。OUT 和 IN OUT不能指定默认值
网友评论