错误:
1. a.非匿名的PLSQL块,is/as后面直接跟变量定义
b.只是匿名的PLSQL块才以declare开头
c.在任何的PLSQL块内部可以在BEGIN 。。。END之间再定义PLSQL块嵌套,嵌套的PLSQL块可以带DECLARE
进行定义
所以你的代码中的
begin
declare
end proc_cancel_digital_id;
这三行可以不要。
2. EXCEPTION部分的rollback也可以不用要
因为你的PLSQL块内部只有SELECT,而不是DELETE,INSERT ,UPDATE。
3. 输出参数strAge,strName,ret_code,v_error_message
a.完全没有规范可言,真希乱
b.string 数据类型是sys.STANDARD 包中定义的子类型 subtype STRING is VARCHAR2;
所以直接用标量类型更好,减少一道转换
(另外一看就知这是搞比如java 之类的 定义习惯)
可参考如下:
create or replace procedure proc_test( p_age IN NUMBER,
p_name IN VARCHAR2,
P_ret_code OUT VARCHAR2,
p_error_msg OUT VARCHAR2
)
as
...
4. EXECUTE IMMEDIATE动态语句
strsql :='select name from student where age=100';
execute immediate strsql using strAge ;
strsql :='select age from teacher where name=jill';
execute immediate strsql using strName ;
a. bind variables 使用错误应该是
strsql :='select name from student where age=:1';
execute immediate strsql using strAge ;
strsql :='select age from teacher where name=:2';
execute immediate strsql using strName ;
b. 没有象你这样用execute immediate strsql
而strsql又只是select的。
一般会带return or returning,如果是select的话
execute immediate strsql return v_age using p_age
execute immediate strsql return v_name using p_name
5. 变量定义部分
strsql varcchar(1024);
KAO,还写错了varcchar 应该是VARCHAR 或 VARCHAR2
其实在系统的包sys.STANDARD中已定义如下:
subtype VARCHAR is VARCHAR2;
subtype STRING is VARCHAR2;
6. 业务处理
"上面有两个select,任何一个查不到数据都会抛异常"
没有定义子块,出了异常,也只是最外层的EXCEPTION捕捉
无法分辨
应该:
BEGIN
BEGIN
strsql :='select name from student where age=:1';
execute immediate strsql return v_name using p_age;
EXCEPTION when ...
....
END;
...
END;
7.
BEGIN
strsql :='select name from student where age=:1';
execute immediate strsql return v_name using p_age;
EXCEPTION when ...
....
END;
直接用,根本不需要用动态SQL
BEGIN
SELECT name
INTO v_name
FROM student
WHERE age = p_age;
EXCEPTION WHEN NO_DATA_FOUND THEN
p_ret_code := sqlcode;
p_error_message := sqlerrm;
END;
...
8。唉,就是个希乱。。。。。。
(无意冒犯你)
要用好,就要从头学SQL/PLSQL。。。。。。