本节内容讲解在数据库中调用存储过程的方法,非应用程序员如不需了解可以跳过,不影响正常阅读。
在数据库的使用中,除了数据表,存储过程也具有很重要的作用。在集算器中,可以方便的调用数据库的存储过程,这里来了解一下在集算器中如何用db.proc() 函数调用各类存储过程。
存储过程有时用来返回查询结果,有时仅仅用来完成数据库操作,而没有返回值。在这里我们先来看如何调用无返回值的存储过程。用oracle的存储过程为例,存储过程proc1只有一个输入参数,没有输出参数:
- create or replace procedure proc1
- (pid IN VARCHAR)
- as
- begin
- insert into emp values(pid,'mike');
- update emp set name='rose' where id=pid;
- commit;
- end;
在集算器中用execute函数或者proc函数都可以来调用这个存储过程:
|
A |
1 |
=connect("ora") |
2 |
>A1.execute("{call proc1(?)}",4) |
3 |
>A1.close() |
A1中连接数据库。A2中用execute函数调用存储过程,输入参数值为4。执行存储过程完毕后,应该在A3中关闭数据库连接。
|
A |
1 |
=connect("ora") |
2 |
>A1.proc("{call proc1(?)}",4:0:"i":) |
3 |
>A1.close() |
A1中连接数据库,A3关闭数据库连接。A2中调用存储过程pro1,和上例不太一样,参数后边添加了描述。集算器中的proc函数主要用来调用有返回值和结果集的存储过程,但也可以用来调用无返回参数的存储过程pro1。
在调用存储过程时设定每个参数的完整格式是a:t:m:v,其中a指参数值,t指参数类型,m指参数输入/输出模式,v指存储过程若有返回值时,存储结果的参数名称。本例中,4:0:"i":定义了一个输入参数,其中4是输入参数的值,0表示输入参数的类型是由集算器自动识别,"i"表示输入类型。如需要手工指定参数类型可以写为:4:1:"i":,中间的1代表整形int。集算器支持的参数类型详见本文的附录:参数类型定义。
对于有返回值的存储过程,就只能用proc函数调用了。下面的存储过程testb要返回一个参数值,所以不能使用execute函数,需要使用proc函数。
- create or replace procedure testb
- (para1 in varchar2,para2 out varchar2)
- as
- begin
- select name into para2 from emp where id= para1;
- end testb;
集算器调用这个存储过程的代码是:
|
A |
1 |
=connect("ora") |
2 |
=A1.proc("{call testb(?,?)}",1:0:"i":,:11:"o":name) |
3 |
=name |
4 |
>A1.close() |
A1中连接数据库,A4中关闭连接。
A2中使用proc函数调用存储过程testb。这里使用了两个参数:1:0:"i":表示值为1,类型为自动判断的输入参数;:11:"o":name中的11代表字符串类型(详见附录:参数类型定义),"o"代表输出类型,name是为这个输出参数定义了一个集算器变量,接收返回值。当
A3中取得变量name的值,即为存储过程的输出结果。变量值的类型由存储过程决定,在本例中name用来返回指定编号员工的名字,类型是字符串。
在存储过程中,共有3种输入/输出模式:输入参数,输出参数,输入输出参数,分别用"i","o"和"io"表示。其中,输入输出参数,表示存储过程中的参数既用来输入数据,同时也被存储过程赋值。
存储过程更多的情况下会被用来返回结果集。如下面的存储过程RQ_TEST_CUR会返回单个结果集:
- CREATE OR REPLACE PROCEDURE RQ_TEST_CUR
- (
- V_TEMP OUT TYPE.RQ_REF_CURSOR,
- PID IN VARCHAR
- )
- AS
- BEGIN
- OPEN V_TEMP FOR SELECT * FROM TEST WHERE ID =PID;
- END RQ_TEST_CUR;
这个存储过程中输入一个参数,并用游标返回了一个结果集。在集算器中调用这个存储过程的代码如下:
|
A |
1 |
=connect("ora") |
2 |
=A1.proc("{call RQ_TEST_CUR(?,?)}",:101:"o":table1,1:0:"i":) |
3 |
=table1 |
4 |
>A1.close() |
A2单元格使用proc函数调用存储过程:=A1.proc("{call RQ_TEST_CUR(?,?)}", :101:"o":table1, 1:0:"i":)。下面依次解释一下proc函数中设定的参数:
SQL字符串"{call RQ_TEST_CUR(?,?)}"中包含调用存储过程的名字,问号表示SQL的参数。
再来看存储过程中的参数:
:101:"o":table1定义了一个输出参数,第一个冒号前留空表示没有输入值,101代表其数据类型是游标,"o"代表这个参数是输出参数。table1是定义了一个变量,可以用这个变量引用返回结果。
1:0:"i":定义了一个输入参数,1是输入参数的值,0表示输入参数的类型是由集算器自动识别,"i"代表这个参数是输入参数,最后一个冒号后留空表示不需要将结果输出。
A3单元格通过使用A2中的输出变量来引用存储过程的执行结果,计算结果与A2是相同的,都是从TEST表中查询的结果,数据类型是序表。
存储过程同样也可以用来返回多个结果集。如下面的oracle存储过程用游标返回两个结果集:
- create or replace procedure proAA
- (
- out_var out sys_refcursor,
- out_var2 out sys_refcursor
- )
- as
- begin
- open out_var for select * from emp;
- open out_var2 for select * from test;
- end;
这个简单的存储过程只是返回了emp和test两个表的结果集。在集算器中调用这个存储过程,接收两个结果集的程序如下:
|
A |
1 |
=connect("ora") |
2 |
=A1.proc("{call proAA(?,?)}",:101:"o":a,:101:"o":b) |
3 |
=A2(1) |
4 |
=a |
5 |
=b |
6 |
>A1.close() |
A2中用proc函数调用存储过程:=A1.proc("{call proAA(?,?)}",:101:"o":a,:101:"o":b),返回了两个结果集(序表),组成了一个序表的集合:序列,赋值给了A2。下面再详细解释一下proc函数中的参数:
SQL字符串"{call proAA(?,?)}"中包含调用存储过程的名字,问号表示SQL的参数。
:101:"o":a中定义了一个输出参数,101代表其数据类型是游标,"o"代表这个参数是输出参数。a是定义了一个变量,可以将返回的结果输出到这个变量,输出参数2。
:101:"o":b中定义了一个输出参数,101代表其数据类型是游标,"o"代表这个参数是输出参数。b是定义了一个变量,可以将返回的结果输出到这个变量。
A3单元格返回了A2单元格的第一个序表(emp表的结果集)。
A4、A5单元格分别使用A2中的输出变量a、b来获取存储过程对应的执行结果,其中a对应emp表的数据,赋值给A4,b对应test表的数据,赋值给A5。A2中的结果其实就等于A4和A5中的序表所构成的序列。
存储过程参数的类型取值如下:
– public final static byte DT_DEFAULT = (byte) 0; |
//默认,自动识别 |
– public final static byte DT_INT = (byte) 1; |
//32位整数 |
– public final static byte DT_LONG = (byte) 2; |
//64位长整数 |
– public final static byte DT_SHORT = (byte) 3; |
//16位短整数 |
– public final static byte DT_BIGINT = (byte) 4; |
//大整数 |
– public final static byte DT_FLOAT = (byte) 5; |
//32位浮点数 |
– public final static byte DT_DOUBLE = (byte) 6; |
//64位双精度浮点数 |
– public final static byte DT_DECIMAL = (byte) 7; |
//十进制长实数 |
– public final static byte DT_DATE = (byte) 8; |
//日期 |
– public final static byte DT_TIME = (byte) 9; |
//时间 |
– public final static byte DT_DATETIME = (byte) 10; |
//日期时间 |
– public final static byte DT_STRING = (byte) 11; |
//字符串 |
– public final static byte DT_BOOLEAN = (byte) 12; |
//布尔值 |
|
|
– public final static byte DT_INT_SERIES = (byte) 51; |
//整数序列 |
– public final static byte DT_LONG_SERIES = (byte) 52; |
//长整数序列 |
– public final static byte DT_SHORT_SERIES = (byte) 53; |
//短整数序列 |
– public final static byte DT_BIGINT_SERIES = (byte) 54; |
//大整数序列 |
– public final static byte DT_FLOAT_SERIES = (byte) 55; |
//浮点数序列 |
– public final static byte DT_DOUBLE_SERIES = (byte) 56; |
//双精度浮点数序列 |
– public final static byte DT_DECIMAL_SERIES = (byte) 57; |
//长实数序列 |
– public final static byte DT_DATE_SERIES = (byte) 58; |
//日期序列 |
– public final static byte DT_TIME_SERIES = (byte) 59; |
//时间序列 |
– public final static byte DT_DATETIME_SERIES = (byte) 60; |
//日期时间序列 |
– public final static byte DT_STRING_SERIES = (byte) 61; |
//字符串序列 |
– public final static byte DT_BYTE_SERIES = (byte) 62; |
//字节序列 |
|
|
– public final static byte DT_CURSOR = (byte) 101; |
//游标 |
– public final static byte DT_AUTOINCREMENT = (byte) 102; |
//自增长字段 |