Dav*_*dEG 2 postgresql polymorphism types stored-procedures plpgsql
问题:如何在存储函数中声明相同类型的变量参数?
简单的答案是使用%TYPE,这有效:
CREATE OR REPLACE FUNCTION test_function_1(param1 text)
RETURNS integer AS
$BODY$
DECLARE
myVariable param1%TYPE;
BEGIN
return 1;
END;
$BODY$
LANGUAGE plpgsql VOLATILE
COST 100;
Run Code Online (Sandbox Code Playgroud)
但问题是何时param1是复合类型:
CREATE TYPE comp_type as
(
field1 text
)
CREATE OR REPLACE FUNCTION test_function_2(param1 comp_type)
RETURNS integer AS
$BODY$
DECLARE
myVariable param1%TYPE;
BEGIN
return 1;
END;
$BODY$
LANGUAGE plpgsql VOLATILE
COST 100;
Run Code Online (Sandbox Code Playgroud)
这不起作用:
ERROR: type comp_type does not exist [SQL State=42704]
Run Code Online (Sandbox Code Playgroud)
那么当param1复合型时我该怎么办?
(注意:myVariable comp_type因为我的功能稍微复杂一点,所以不是一个好选择.)
编辑:我在复制和粘贴时出错,真正的错误是:
ERROR: invalid type name "param1%TYPE"
Position: 130 [SQL State=42601]
Run Code Online (Sandbox Code Playgroud)
并使用param1%ROWTYPE错误是:
ERROR: relation "param1" does not exist
Where: compilation of PL/pgSQL function "test_function_2" near line 3 [SQL State=42P01]
Run Code Online (Sandbox Code Playgroud)
%ROWTYPE在那种情况下使用.
AH和DavidEG的测试表明这不起作用.有趣的问题!
你可以尝试一种解决方法.只要您的定义与示例类似,您就可以简单地使用
CREATE FUNCTION test(param1 comp_type)
RETURNS integer AS
$BODY$
DECLARE
myvar comp_type;
BEGIN
return 1;
END;
$BODY$
LANGUAGE plpgsql VOLATILE;
Run Code Online (Sandbox Code Playgroud)
但你真正的问题可能并不那么简单吗?
正如所料,真正的问题更复杂:多态输入类型.该场景的
解决方法更难,但应该完美无缺:
CREATE FUNCTION test(param1 anyelement, OUT a integer, OUT myvar anyelement)
RETURNS record AS
$BODY$
BEGIN
myvar := $1; -- myvar has now the required type.
--- do stuff with myvar.
myvar := NULL; -- reset if you don't want to output ..
a := 1;
END;
$BODY$
LANGUAGE plpgsql VOLATILE;
Run Code Online (Sandbox Code Playgroud)
呼叫:
SELECT a FROM test('("foo")'::comp_type); -- just retrieve a, ignore myvar
Run Code Online (Sandbox Code Playgroud)
查看完整输出:
SELECT * FROM test('("foo")'::comp_type);
Run Code Online (Sandbox Code Playgroud)
v9.0中有一个重要的更新.我引用发行说明:
- 允许在PL/pgSQL函数中为输入参数赋值(Steve Prentice)
以前,输入参数被视为声明为CONST,因此函数的代码无法更改其值.已删除此限制以简化从未强加等效限制的其他DBMS移植函数的过程.输入参数现在的作用类似于初始化为传入值的局部变量.
因此,除了我的解决方法之外,您还可以直接使用输入变量.