我有两个函数,它们都返回一个TYPE,即:
CREATE OR REPLACE FUNCTION myUser.f_myFunction
(
myId IN RAW := NULL
) RETURN myUser.myType
AS
ResultTable myUser.myType;
BEGIN
...
-- fill ResultTable
...
RETURN ResultTable;
END;
现在我想在SELECT语句中加入它们:
SELECT *
FROM myUser.f_myFunction1() f1
JOIN myUser.f_myFunction2() f2 ON f1.xy = f2.yz;
但是如果我在SELECT语句中包含一个函数,我会收到一个错误:
SELECT * FROM myUser.f_myFunction();
*
ERROR in Line 1:
ORA-00933: SQL command not properly ended
ORA-04044: procedure, function, package, or type is not allowed here
.
编辑:将函数调用嵌套在TABLE()子句中会出现以下错误:
SELECT * FROM TABLE(myUser.f_myFunction())
*
ERROR at line 1:
ORA-22905: cannot access rows from a non-nested table item
然后我试着施展它,但是:
SELECT * FROM TABLE(CAST(myUser.f_myFunction() AS myUser.myType))
*
ERROR at line 1:
ORA-22907: invalid CAST to a type that is not a nested table or VARRAY
和:
SELECT * FROM TABLE(CAST(myUser.f_myFunction() AS myUser.myTypeTable))
*
ERROR at line 1:
ORA-00932: inconsistent datatypes: expected - got myUser.myType
.
编辑2:这是类型的定义(对不起,应该包括在前面):
CREATE TYPE myUser.myType AS OBJECT (
....
);
CREATE TYPE myUser.myTypeTable IS TABLE OF myUser.myType;
.
编辑3:让它像这样工作:
CREATE OR REPLACE FUNCTION myUser.f_myFunction
(
myId IN RAW := NULL
) RETURN myUser.myTypeTable
AS
ResultTable myUser.myTypeTable;
BEGIN
SELECT myUser.myType(x.Column1, x.Column2, ...)
BULK COLLECT INTO ResultTable
FROM myUser.myTable x
WHERE ...
RETURN ResultTable;
END;
最佳答案 至少有三种方法可以做到这一点:1)CCreate嵌套表2)多次调用函数3)创建一个函数来访问每个属性.
示例对象
create or replace type myType as object
(
wx number,
xy number
);
CREATE OR REPLACE FUNCTION f_myFunction
(
myId IN RAW := NULL
) RETURN myType
AS
ResultTable myType := myType(1, 2);
BEGIN
RETURN ResultTable;
END;
/
方法1:创建嵌套表
正如Luke Woodward指出的那样,功能TABLE和CAST需要一个嵌套的类型表.即使您只打算使用单个元素.
create or replace type myType_nt is table of myType;
CREATE OR REPLACE FUNCTION f_myFunction_nt
(
myId IN RAW := NULL
) RETURN myType_nt
AS
ResultTable myType_nt := myType_nt(myType(1, 2));
BEGIN
RETURN ResultTable;
END;
/
select wx, xy from table(f_myFunction_nt());
WX XY
-- --
1 2
方法2:对每个属性重复函数调用
如果为每个属性调用一次函数,则不需要额外的对象.这是重复的并且可能是昂贵的.将函数设置为确定性可能会阻止函数实际被多次调用.
select wx, xy from
(
select f_myFunction().wx wx, f_myFunction().xy xy from dual
);
WX XY
-- --
1 2
似乎应该有一个更简单的方法来做到这一点. Oracle确实支持调用该函数一次并返回具有这两个属性的类型.但是没有办法有意义地使用那种类型. SQL无法轻松访问这些属性.
SQL> select * from (select f_myFunction() from dual);
F_MYFUNCTION()(WX, XY)
-----------------------------------------------------
MYTYPE(1, 2)
简单地使用每个属性名称的直观方式不起作用.
SQL> select wx, xy from (select f_myFunction() from dual);
select wx, xy from (select f_myFunction() from dual)
*
ERROR at line 1:
ORA-00904: "XY": invalid identifier
方法3:为每个属性创建一个函数
您可以使用函数访问属性.这需要添加新对象,但它保持您的主要功能相同.
create or replace function get_wx(p_myType myType) return number is
begin
return p_myType.wx;
end;
/
create or replace function get_xy(p_myType myType) return number is
begin
return p_myType.xy;
end;
/
select get_wx(asdf) wx, get_xy(asdf) xy
from (select f_myFunction() asdf from dual);
WX XY
-- --
1 2