oracle - 是否可以将带有参数的游标作为过程的参数传递?

标签 oracle plsql

我有很多类似的处理要做,我想为其制作一个 pl/sql 脚本。 通过查看代码而不是解释它更容易理解,所以这里是一个简化版本:

create or replace package my_test as
  cursor my_cursor(my_filter NUMBER) is select column1, column2 from mytable where column3 = my_filter;
  cursor my_cursor2(my_filter VARCHAR2) is select column1, column2 from mytable where column4 LIKE my_filter;
  -- ...

  procedure test1;
  procedure test2(p_cursor XXX);
  function test3(test_record XXX%ROWTYPE) return number;

end my_test;
/

create or replace package body my_test as
  procedure test1 is    
  begin
    test2(my_cursor(3));
    test2(my_cursor2('foo%'));
    test2(my_cursor(5));
    -- ...
  end test1;

  procedure test2(p_cursor XXX) is
    tmp number;
  begin
    for r in p_cursor loop      
      --some actions 
      tmp := test3(r);
      --some actions
    end loop;
  end test2;

  function test3(test_record XXX%ROWTYPE) return number is
    tmp_sum number;
  begin
    -- ...
    tmp_sum := test_record.column1 + test_record.column2;
    -- ...
    return l_summ;
  end test3;


end my_test;
/

BEGIN
    my_test.test1();
END;
/

我已经尽力了,但没有成功。也许有人可以帮助我?有可能实现这样的事情吗?我应该用什么来代替 XXX

最佳答案

定义记录类型以匹配您要执行的查询的投影。您可以使用它来定义 test3() 的 IN 参数。

定义一个返回该记录类型的引用游标。您可以使用它来定义 test2() 的 IN 参数。

定义返回由该游标类型定义的引用游标的函数,而不是游标。

所以你的包看起来像这样:

create or replace package my_test as

  type t_record is record(
     column1 mytable.column1%type
    ,column2 mytable.column2%type
  );

  type t_cursor is ref cursor return t_record;

  function my_cursor (my_filter NUMBER)   return t_cursor ;
  function my_cursor2(my_filter VARCHAR2) return t_cursor ;

  procedure test1;
  procedure test2(p_cursor t_cursor);
  function  test3(test_record t_record) return number;

end my_test;
/

实现如下所示(带有一些输出以使演示更容易理解):

create or replace package body my_test as

  function my_cursor(my_filter NUMBER) return t_cursor is 
      rc sys_refcursor;
  begin
    open rc for  select column1, column2 from mytable where column3 = my_filter;
    return rc;
  end my_cursor;

  function my_cursor2(my_filter VARCHAR2)  return t_cursor is 
      rc sys_refcursor;
  begin
    open rc for  select column1, column2 from mytable where column4 LIKE my_filter;
    return rc;
  end my_cursor2;

  procedure test1 is    
  begin
    dbms_output.put_line('test2(my_cursor, 3)');
    test2(my_cursor(3)); 
    dbms_output.put_line('test2(my_cursor2, foo');
    test2(my_cursor2('foo%'));
    dbms_output.put_line('test2(my_cursor,5)');
    test2(my_cursor(5));
    -- ...
  end test1;

  procedure test2(p_cursor t_cursor) is
    tmp number;
    l_rec t_record;
  begin
    loop
      fetch p_cursor into l_rec;
      exit when p_cursor%notfound;
      --some actions 
      tmp := test3(l_rec);
      dbms_output.put_line(l_rec.column1 ||'+'||l_rec.column2||'='||tmp);
      --some actions
    end loop;
    close p_cursor;
  end test2;

  function test3(test_record t_record) return number is
    tmp_sum number;
  begin
    -- ...
    tmp_sum := test_record.column1 + test_record.column2;
    -- ...
    return tmp_sum;
  end test3;

end my_test;
/

我说的是演示吗?当然有a demo on db<>fiddle .

关于oracle - 是否可以将带有参数的游标作为过程的参数传递?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/60093505/

相关文章:

sql - 为什么确定性函数在 SQL 中执行额外的时间?

string - 使用ANTLR解析字符串文字时,出现NoViableAltException

oracle - PL/SQL 上的 get_detailed_sqlerrm 语法

oracle - 计算汉明距离的索引访问

sql-server - 向表中添加 BLOB 字段的性能开销

sql - 解决Oracle SQL中的 "single-row subquery returns more than one row"错误

sql - PL/SQL TEXT_IO 包

sql查询优化

c - OCIDate 在进入 Oracle 的过程中被破坏

java - 如何从一台服务器更新另一台服务器中的表