3

私は次のことをしていますが、うまくいきません

select package_name.function_name(param,param) from dual

カーソルを返す関数を呼び出しているので、推測"from dual"が問題になります

それを行う別の方法はありますか?

4

3 に答える 3

2

私はあなたが参照カーソルを意味していると思います。これは、クエリによって返される一連のレコードへのポインタとして機能するPL/SQL構造です。これは、クエリを実行するクライアントが解釈する必要があることを意味します。たとえば、RefCursorをJDBCまたはODBCResultSetにマップできます。

あなたの基本的な声明には確かに何も悪いことはありません。これがあなた自身に似た関数です:

SQL> desc get_emps
FUNCTION get_emps RETURNS REF CURSOR
 Argument Name                  Type                    In/Out Default?
 ------------------------------ ----------------------- ------ --------
 P_DNO                          NUMBER(2)               IN
 P_SORT_COL                     VARCHAR2                IN     DEFAULT
 P_ASC_DESC                     VARCHAR2                IN     DEFAULT

SQL> 

これは、より広いPL/SQLブロックで簡単に呼び出すことができます。

SQL> declare
  2      rc sys_refcursor;
  3  begin
  4      rc := get_emps(50);
  5  end;
  6  /

PL/SQL procedure successfully completed.

SQL>

ただし、SQL*PLusはCURSOR構造をネイティブに処理できます。

SQL> select get_emps(50) from dual
  2  /

GET_EMPS(50)
--------------------
CURSOR STATEMENT : 1

CURSOR STATEMENT : 1

     EMPNO ENAME      JOB              MGR HIREDATE         SAL       COMM     DEPTNO
---------- ---------- --------- ---------- --------- ---------- ---------- ----------
      8060 VERREYNNE  PLUMBER         8061 08-APR-08       4000                    50
      8061 FEUERSTEIN PLUMBER         7839 27-FEB-10       4500                    50
      8085 TRICHLER   PLUMBER         8061 08-APR-10       3500                    50
      8100 PODER      PLUMBER         8061                 3750                    50


SQL>

このステートメントはSQLDeveloperでも実行されますが、結果セットは見苦しい方法でレイアウトされています。

したがって、関数に問題がある場合、質問は次のとおりです。

  1. どのクライアント環境を使用していますか?
  2. どのように正確に「機能しない」のでしょうか。エラーメッセージを含め、観察された動作を説明してください。
  3. また、データベースのバージョン、OSなどの環境の詳細も教えてください。

このトピックに関する他の質問を読んだので、問題は(組み込みではなく)ユーザー定義の参照カーソルの使用が原因である可能性があると思いました。ただし、それでも違いはありません。このパッケージ化された関数:

SQL> create or replace package emp_rc_utils as
  2
  3      type emp_rc is ref cursor return emp%rowtype;
  4
  5      function       get_emps
  6          ( p_dno in emp.deptno%type
  7      )
  8      return emp_rc;
  9  end;
 10  /

Package created.

SQL> create or replace package body emp_rc_utils as
  2
  3      function       get_emps
  4          ( p_dno in emp.deptno%type
  5      )
  6          return emp_rc
  7      is
  8          return_value emp_rc_utils.emp_rc;
  9      begin
 10
 11          open return_value for select * from emp where deptno = p_dno;
 12
 13          return return_value;
 14      end get_emps;
 15
 16  end emp_rc_utils;
 17  /

Package body created.

SQL>

まだ動作します...

SQL> declare
  2      rc sys_refcursor;
  3  begin
  4      rc := emp_rc_utils.get_emps(50);
  5  end;
  6  /

PL/SQL procedure successfully completed.


SQL> select emp_rc_utils.get_emps(50) from dual
  2  /

EMP_RC_UTILS.GET_EMP
--------------------
CURSOR STATEMENT : 1

CURSOR STATEMENT : 1

     EMPNO ENAME      JOB              MGR HIREDATE         SAL       COMM     DEPTNO
---------- ---------- --------- ---------- --------- ---------- ---------- ----------
      8085 TRICHLER   PLUMBER         8061 08-APR-10       3500                    50
      8060 VERREYNNE  PLUMBER         8061 08-APR-08       4000                    50
      8061 FEUERSTEIN PLUMBER         7839 27-FEB-10       4500                    50
      8100 PODER      PLUMBER         8061                 3750                    50


SQL>
于 2011-01-06T13:21:27.460 に答える
1

これは、refcursor呼び出しを介して行うか、ユーザー定義テーブルにデータを入力して、次のように返すことができます。

create or replace
function getRef return sys_refcursor
is
l_ref  sys_refcursor;
begin

    open l_ref for
    select 1 a, 'a' c from dual
    union all
    select 2 a, 'b' c from dual
    union all
    select 3 a, 'c' c from dual
    union all
    select 4 a, 'd' c from dual;

    return l_ref;

end getRef;
/

select getref() from dual;

GETREF() 
-------- 
A                      C  
---------------------- -  
1                      a  
2                      b  
3                      c  
4                      d  

--you'll notice this isn't the most user-friendly result set if you look at it in SQL Developer or whatno
--drop function getRef;

テーブルコレクションをそのまま返す場合は、「テーブル」を使用することもできます。

create or replace type lookup_row as 
  object ( a number, c varchar2(20) );
  /
create or replace type lookups_tab as 
  table of lookup_row;
/

create or replace
function getUserDefinedTableType return lookups_tab
is
lTestTypeTable  lookups_tab;
begin

     SELECT lookup_row(a,c)
               bulk collect INTO lTestTypeTable
               from
    (select 1 a, 'a' c from dual
    union all
    select 2 a, 'b' c from dual
    union all
    select 3 a, 'c' c from dual
    union all
    select 4 a, 'd' c from dual);

    return lTestTypeTable;

end getUserDefinedTableType;
/


select * from table(getUserDefinedTableType());
--this returns it in a more user friendly manner
--http://www.oreillynet.com/pub/a/network/2003/01/22/feuerstein.html?page=2
--http://stackoverflow.com/questions/3150137/converting-oracle-query-into-user-defined-types-in-pl-sql/3152885#3152885
A                      C                    
---------------------- -------------------- 
1                      a                    
2                      b                    
3                      c                    
4                      d  
于 2011-01-06T13:19:57.307 に答える
0

やってみました:

myCursor := package_name.function_name(param,param);

これは、テストブロックまたはストアドプロシージャ内からのものである必要があります。

于 2011-01-06T11:50:19.897 に答える