如何在postgres的函数中传递数组并修改它
Posted
技术标签:
【中文标题】如何在postgres的函数中传递数组并修改它【英文标题】:How to pass and array and modify it in a function in postgres 【发布时间】:2018-08-23 15:45:02 【问题描述】:我正在尝试编写一个执行此操作的函数:基本上创建一个数组,其数据元素与传递给函数的数组相同,但有时会发生一些变化——比如如果某个元素是偶数,那么标志应该从 N 改变到 Y。该过程将一个包含两个元素的数组作为输入 - 一个数字和一个标志。例如。 (1,'N'), (2,'N')。现在,如果传递的数字是偶数,那么 proc 应该修改该值并更改为 (2,'Y'),而另一个保持为 (1,'N')。
基本上我的数组基础知识并不清晰,阅读细节并没有帮助,所以这个问题。
我尝试了以下方法,但它不起作用...您能建议一下吗:
CREATE TYPE test_n_t_num AS (
v_n double precision,
is_even character varying(1));
create function temp_n_proc_2(p_nums IN OUT test_n_t_num[])
as
$$
declare
v_nums test_n_t_num[];
v_cnt double precision;
BEGIN
v_cnt := cardinality(p_nums);
v_nums := ARRAY[]::test_n_t_num[];
for i in 1..v_cnt LOOP
if p_nums[i].v_n_double % 2 = 0 then
v_nums [i].is_even := 'Y';
p_nums [i].is_even := 'Y'
else
v_nums [i].is_even := p_nums [i].is_even;
end if;
v_nums[i] := p_nums[i].v_n,v_nums [i].is_even;
END LOOP;
END;
$$
language plpgsql;
稍后我还需要循环并打印出数组 v_nums 中的值 - 一个在函数中定义的值。
谢谢你, 尼拉夫
【问题讨论】:
好吧,我什至无法在我的系统上创建它,它不喜欢函数的语法。但是不管怎样,你的返回值是p_nums
,但你的大部分作业都是v_nums
...对吗?
是的,我也只想设置 v_nums(在我通过这个问题建模的实际工作问题中,我需要打印出 v_nums)。而且我对语法非常混乱。而且我也在编辑 p_nums 一次。
【参考方案1】:
当我过去尝试做这种事情时,我遇到了类似的问题。基本上你不能使用数组表示法分配给复合对象,即your_array[1].field := value
不起作用。这是可以做到的(我不使用cardinality
,因为我仍在使用 9.3 并且是在 9.4 中添加的):
CREATE TYPE public.test1 AS (a INTEGER, is_even BOOLEAN);
CREATE OR REPLACE FUNCTION f1(ar INOUT public.test1[]) AS $$
DECLARE
t public.test1;
BEGIN
RAISE NOTICE '%', ar;
FOR i IN 1..ARRAY_LENGTH(ar, 1) LOOP
t := ar[i];
t.is_even := t.a % 2 = 0;
ar[i] := t;
END LOOP;
RAISE NOTICE '%', ar;
END
$$ LANGUAGE plpgsql;
所以基本上创建一个该类型的变量,将索引项读入变量,修改字段,然后将变量的内容复制回数组。
SELECT * FROM f1('"(1,)","(4,)","(6,)"'::public.test1[])
返回"(1,f)","(4,t)","(6,t)"
打印的消息(这是使用 pgadmin 3)是:
NOTICE: "(1,)","(4,)","(6,)"
NOTICE: "(1,f)","(4,t)","(6,t)"
【讨论】:
非常感谢 Eurotrash!我在文档中没有看到任何地方指出了这些细节。这很棘手!还有一个问题。如果在函数中我想打印出传递的原始数组和修改后的数组怎么办。这可能吗? @dbusern 不确定我是否理解您所说的打印的意思 - 请参阅上面的编辑,是这样吗?由于输入和输出使用相同的数组变量,要打印原始版本,我需要在开始时调用 RAISE NOTICE,然后再进行任何修改。然后在它返回之前的最后,它再次打印修改后的数组。 嗨 Eurotrash,我明白了。我的错。我应该说的是;应用程序需要返回修改后的数组。我想你已经提供了细节。我将测试并在明天之前确认是否可行。再次感谢。 @Eurotrash。不能感谢你。它就像你说的那样工作,完全解决了我的问题。这是一个非常好的帮助。谢谢!!!!以上是关于如何在postgres的函数中传递数组并修改它的主要内容,如果未能解决你的问题,请参考以下文章
如何通过在 swift playground 中传递 Int 数组来创建求和函数并调用它?
如何使用 Postgres 数据库 url 字符串传递证书路径以进行 SSL 连接