nny*_*yby 3 postgresql plpgsql postgresql-9.1
我在PostgreSQL文档中找不到任何显示如何声明记录或行,同时声明元组结构的内容.如果您没有定义元组结构,则会收到错误"尚未分配的记录的元组结构是不确定的".
这就是我现在正在做的,它工作正常,但必须有一个更好的方法来做到这一点.
CREATE OR REPLACE FUNCTION my_func()
RETURNS TABLE (
"a" integer,
"b" varchar
) AS $$
DECLARE r record;
BEGIN
CREATE TEMP TABLE tmp_t (
"a" integer,
"b" varchar
);
-- Define the tuple structure of r by SELECTing an empty row into it.
-- Is there a more straight-forward way of doing this?
SELECT * INTO r
FROM tmp_t;
-- Now I can assign values to the record.
r.a := at.something FROM "another_table" at
WHERE at.some_id = 1;
-- A related question is - how do I return the single record 'r' from
-- this function?
-- This works:
RETURN QUERY
SELECT * FROM tmp_t;
-- But this doesn't:
RETURN r;
-- ERROR: RETURN cannot have a parameter in function returning set
END; $$ LANGUAGE plpgsql;
Run Code Online (Sandbox Code Playgroud)
Erw*_*ter 12
您正在混合返回SETOF值的语法以及返回单个行或值的语法.
- 一个相关的问题是 - 如何从中返回单个记录'r'
使用声明函数时RETURNS TABLE,必须RETURN NEXT在正文中使用返回行(或标量值).如果你想使用一个record变量,它必须匹配返回类型.请进一步参考代码示例.
如果您只想返回单行,则不需要未定义类型的记录.@Kevin已经展示了两种方式.我将添加一个带OUT参数的简化版本:
CREATE OR REPLACE FUNCTION my_func(OUT a integer, OUT b text)
AS
$func$
BEGIN
a := ...;
b := ...;
END
$func$ LANGUAGE plpgsql;
Run Code Online (Sandbox Code Playgroud)
您甚至不需要添加RETURN;函数体,声明OUT参数的值将在函数结束时自动返回 - NULL对于尚未分配的任何参数.
而且您不需要声明,RETURNS RECORD因为OUT参数已经清楚了.
如果您确实想要返回多行(包括0行或1行的可能性),则可以将返回类型定义为RETURNS...
SETOF some_type,some_type可以是任何已注册的标量或复合类型.
TABLE (col1 type1, col2 type2) - 临时行类型定义.
SETOF record加上OUT参数来定义列名和类型.
100%相当于RETURNS TABLE.
SETOF record无需进一步定义.但是返回的行是未定义的,您需要在每次调用时包含列定义列表(请参阅示例).
记录变量类似于行型变量,但它们没有预定义的结构.它们采用SELECT或FOR命令期间分配的行的实际行结构.
还有更多,请阅读手册.
您可以使用记录变量而无需指定已定义的类型,甚至可以返回此类未定义的记录:
CREATE OR REPLACE FUNCTION my_func()
RETURNS SETOF record AS
$func$
DECLARE
r record;
BEGIN
r := (1::int, 'foo'::text); RETURN NEXT r; -- works with undefined record
r := (2::int, 'bar'::text); RETURN NEXT r;
END
$func$ LANGUAGE plpgsql;
Run Code Online (Sandbox Code Playgroud)
呼叫:
SELECT * FROM my_func() AS x(a int, b text);
Run Code Online (Sandbox Code Playgroud)
但这非常难以处理,因为您必须为每次调用提供列定义列表.它通常可以用更优雅的东西代替:
RETURNS TABLE或朋友).CREATE OR REPLACE FUNCTION my_func()
RETURNS SETOF tbl_or_type AS
$func$
DECLARE
r tbl_or_type;
BEGIN
SELECT INTO tbl_or_type * FROM tbl WHERE id = 10;
RETURN NEXT r; -- type matches
SELECT INTO tbl_or_type * FROM tbl WHERE id = 12;
RETURN NEXT r;
-- Or simpler:
RETURN QUERY
SELECT * FROM tbl WHERE id = 14;
END
$func$ LANGUAGE plpgsql;
Run Code Online (Sandbox Code Playgroud)
你的问题不清楚你究竟需要什么.
| 归档时间: |
|
| 查看次数: |
16157 次 |
| 最近记录: |