【问题标题】:Loop of composite type as stored procedure input PostgreSQL复合类型的循环作为存储过程输入 PostgreSQL
【发布时间】:2017-04-18 19:17:16
【问题描述】:

我通过传递一个类型来创建一个存储过程,并在过程中执行一个循环,以便我可以插入每个信息类型

这是我的类型

 create type leketo as(id integer, name text);

在我的类型中插入行的函数

 CREATE OR REPLACE FUNCTION getLeketo()
  RETURNS SETOF leketo AS
$BODY$
declare
l leketo;
begin

l.id := 1;
l.name := 'One';
return next l;

l.id := 2;
l.name := 'Two';
return next l;


l.id := 3;
l.name := 'Three';
return next l;


l.id := 4;
l.name := 'Four';
return next l;

l.id := 5;
l.name := 'Five';
return next l;

end
$BODY$
  LANGUAGE plpgsql VOLATILE;

运行函数会将这个返回给我

select * from getLeketo()

1  One 
2  Two 
3  Three 
4  Four 
5  Five 

在此过程中,我们将遍历所有行

CREATE OR REPLACE FUNCTION loopLeketo(pl leketo)
  RETURNS void AS
$BODY$
declare
l leketo;
begin

 for l in (select * from pl) loop
  raise notice '----------------------------------------';
  raise notice 'id=%, name=%', l.id, l.name;
 end loop;
end
$BODY$
  LANGUAGE plpgsql VOLATILE;

如果我尝试这样做,我会收到以下消息

DO $$
declare
l leketo;
begin
select * from getLeketo() into l;
PERFORM loopLeketo(l);
end$$;

错误:关系“pl”不存在

【问题讨论】:

    标签: arrays postgresql stored-procedures types plpgsql


    【解决方案1】:

    您收到该错误消息是因为参数(在您的情况下为 pl)不能出现在查询的 FROM 子句中,因此 PostgreSQL 会将 pl 解释为表名。

    更深层次的问题是您尝试将一组值分配给单个变量,这是行不通的。您的SELECT ... INTO 语句只会将第一个结果存储在变量l 中。

    你没有告诉我们你真正想要实现什么,但我可以想到两种方法来解决你所展示的问题:

    1. 对查询结果一一处理。 PL/pgSQL 代码如下所示:

      DEFINE
         l leketo;
      BEGIN
         FOR l IN SELECT * FROM getleketo() LOOP
            RAISE NOTICE 'id=%, name=%', l.id, l.name;
         END LOOP;
      END;
      
    2. getleketo() 定义为RETURNS SETOF leketo,而不是RETURNS refcursor,并让它返回结果的游标。然后,您可以将整个查询结果分配给refcursor 类型的变量,并将其用作loopleketo 函数的参数。

      详情请见the documentation

    【讨论】:

      猜你喜欢
      • 2013-10-15
      • 2018-01-01
      • 2021-10-28
      • 1970-01-01
      • 2020-09-19
      • 1970-01-01
      • 1970-01-01
      • 2018-07-05
      • 1970-01-01
      相关资源
      最近更新 更多