支持我功能中任何类型的记录

时间:2018-12-11 13:57:52

标签: postgresql

PL/pgSQL函数不同,语言SQL的函数接受记录和记录数组。以下脚本有效:

create type testtyp1 as ( a int, b unknown );
create type testtyp2 as ( a int, b text );
create type testtyp3 as ( a int, b varchar(8000) );

create or replace function xdecode(variadic args anyarray) RETURNS text AS $$
  select 'x'::text;
$$ LANGUAGE sql;

-- the function should support all these:
select xdecode( (1,'a'),(2,'b') );
select xdecode( (1,'a')::testtyp1, (2,'b')::testtyp1 );
select xdecode( (1,'a')::testtyp2, (2,'b')::testtyp2 );
select xdecode( (1,'a')::testtyp3, (2,'b')::testtyp3 );

同样重要的是:

select xdecode( (0.1,now()), (0.2,now()) );

现在,我需要更改函数,以便它返回其第一列符合特定条件的数组元素的第二列。

问题在于记录列可以具有任何名称或完全没有名称。另一个问题是PostgreSQL中的字符常量具有类型:unknown

如果我尝试将行强制转换为其他任何类型,则调用将失败,并显示以下信息:

create or replace function xdecode(variadic args anyarray) RETURNS text AS $$
  select args[1]::testtyp1::text
$$ LANGUAGE sql;
...
> select xdecode( (1,'a'),(2,'b') );
cannot cast type record to testtyp1
> select xdecode( (1,'a')::testtyp3, (2,'b')::testtyp3 );
cannot cast type testtyp3 to testtyp1

我可以通过一个辅助函数来避免不知道列名:

create or replace function hlp(arg anyelement) RETURNS record AS $$
  select arg;
$$ LANGUAGE sql;

create or replace function xdecode(variadic args anyarray) RETURNS text AS $$
  select b::text from hlp( args[1] ) AS T(a int , b unknown);
$$ LANGUAGE sql;

但是我不知道是unknown还是text

> select xdecode( (1,'a'),(2,'b') );
a
> select xdecode( (1,'a')::testtyp1, (2,'b')::testtyp1 );
a
> select xdecode( (1,'a')::testtyp2, (2,'b')::testtyp2 );
Returned type text at ordinal position 2, but query expects unknown.
> select xdecode( (1,'a')::testtyp3, (2,'b')::testtyp3 );
Returned type text at ordinal position 2, but query expects unknown.

不能指定类型:

create or replace function xdecode(variadic args anyarray) RETURNS text AS $$
  select b::text from hlp( args[1] ) AS T(a, b);
$$ LANGUAGE sql;
> select xdecode( (1,'a'),(2,'b') );
a column definition list is required for functions returning "record"

0 个答案:

没有答案