【问题标题】:pass pl/sql record as arguement to procedure将 pl/sql 记录作为参数传递给过程
【发布时间】:2013-10-28 13:58:00
【问题描述】:

如何将 pl/sql 记录类型传递给过程:

CREATE OR REPLACE PACKAGE BODY PKGDeleteNumber
AS
 PROCEDURE deleteNumber (
    list_of_numbers  IN List_Numbers
 )
 IS
   i_write VARCHAR2(5);
 BEGIN
   --do something
 END deleteNumber;

END PKGDeleteNumber;
/

在这个过程中deleteNumber我使用了List_Numbers,这是一个记录类型。相同的包声明是:

CREATE OR REPLACE PACKAGE PKGDeleteNumber
AS
   TYPE List_Numbers IS RECORD (
     IID NUMBER
   );
  TYPE list_of_numbers IS TABLE OF List_Numbers;
  PROCEDURE deleteNumber (
    list_of_numbers  IN List_Numbers
  );
END PKGDeleteNumber;

我必须执行过程deleteNumber 传递值列表。我在temp_test 表中插入了数字,然后使用游标 U 从中获取数据:

   SELECT *
     BULK COLLECT INTO test1
     FROM temp_test;

现在,调用我正在使用的过程

execute immediate  'begin PKGDELETENUMBER.DELETENUMBER(:1); end;' 
  using test1;

我也尝试了很多其他的东西(for loopdbms_binding 等)。如何将 pl/sql 记录类型作为参数传递给过程?

编辑:

基本上,我想传递一个数字列表,仅使用本机动态 sql...

添加表 temp_test defn(无索引或约束):

create table test_temp ( 
   IID number
);

然后使用普通的insert 语句插入 1,2,3,4,5。

对于这个解决方案,

In a package testproc
CREATE TYPE num_tab_t IS TABLE OF NUMBER;

CREATE OR REPLACE PROCEDURE my_dyn_proc_test (p_num_array IN num_tab_t) AS
BEGIN
  dbms_output.put_line(p_num_array.COUNT);
END;
/

这是从 sql 提示符/toad 调用的 宣布 v_tab testproc.num_tab_t := testproc.num_tab_t(1, 10); 开始 立即执行'开始 testproc.my_dyn_proc_test(:1);结尾;'使用 v_tab; 结束;

这不起作用。这显示错误。我不在我的工作站,所以现在无法重现该问题。

【问题讨论】:

  • 你没有显示test1的定义,你得到一个错误?请出示。
  • 这是一个简单的表格,里面有 5 个数字...将放定义
  • 你试过收藏吗?
  • 为什么要为此使用本机动态 SQL (EXECUTE IMMEDIATE)?
  • 有一些项目要求,因为我必须只使用动态 sql..

标签: oracle plsql


【解决方案1】:

您不能在EXECUTE IMMEDIATE 语句的USING 子句中使用RECORD 类型。如果你只是想传递一个数字列表,为什么不直接使用TABLE OF NUMBER 类型的变量呢?检查以下示例:

CREATE TYPE num_tab_t IS TABLE OF NUMBER;

CREATE OR REPLACE PROCEDURE my_dyn_proc_test (p_num_array IN num_tab_t) AS
BEGIN
  dbms_output.put_line(p_num_array.COUNT);
END;
/

DECLARE
  v_tab num_tab_t := num_tab_t(1, 10);
BEGIN
  EXECUTE IMMEDIATE 'BEGIN my_dyn_proc_test(:1); END;' USING v_tab;
END;

输出:

2

编辑

试试这个:

CREATE TYPE num_tab_t IS TABLE OF NUMBER;

CREATE OR REPLACE PACKAGE testproc AS
  PROCEDURE my_dyn_proc_test (p_num_array IN num_tab_t);
END;
/

CREATE OR REPLACE PACKAGE BODY testproc AS
  PROCEDURE my_dyn_proc_test (p_num_array IN num_tab_t) AS
  BEGIN
    dbms_output.put_line(p_num_array.COUNT);
  END;
END;
/

DECLARE
  v_tab num_tab_t := num_tab_t(1, 10);
BEGIN
  EXECUTE IMMEDIATE 'BEGIN testproc.my_dyn_proc_test(:1); END;' USING v_tab;
END;

【讨论】:

  • 当我使用不同的包时这不起作用。你也有解决方案吗?
  • @subodh1989 你什么意思?这是一个通用的解决方案,对于每个应该是数字数组的参数,您必须在每个过程/函数中使用 num_tab_t 类型。请编辑您的问题以表明您的意思是它不适用于其他软件包。
  • @subodh1989 检查我编辑的答案。基本上,num_tab_t 类型必须在包外声明,如我的示例所示。
【解决方案2】:

使用对象类型。对象类型对所有包可见

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2013-03-16
    • 1970-01-01
    • 2012-06-23
    • 1970-01-01
    相关资源
    最近更新 更多