在PostgreSQL 9.4中,我有一个接受记录(表条目)作为输入参数的函数。函数是STRICT
,所以我希望如果输入是空记录(例如(NULL,NULL,NULL)
),则不会调用该函数,我会得到NULL
输出。这是期望的行为,因为我的函数计算成本很高。
但PostgreSQL似乎认为在决定是否调用该函数时,空记录确实不为空,并且无论如何都要调用我的昂贵函数,从而导致垃圾输出。请注意,该函数是用C
编写的,我没有费心处理NULL
输入,因为我使用了STRICT
关键字。
这是一个用来说明问题的小例子:
create table test_table as
select null::int as a, null::int as b;
create function rec_func(test_table) returns text as
$$
select 'Function got called'::text;
$$
language sql strict;
select t, t is null as is_null, coalesce(t,(1,2)::test_table), rec_func(t)
from test_table t;
选择查询的输出:
t is_null coalesce rec_func
test_table boolean test_table text
---------- ------- ---------- -------------------
(,) t (,) Function got called
根据IS NULL
运算符,输入记录(,)确实是NULL
,但coalesce()
返回(,),就好像它不是null
和{{ 1}}被调用,好像它是rec_func()
。
not null
和NULL
函数使用的coalesce()
输入的PostgreSQL内部检查与STRICT
运算符不同。有什么想法发生了什么?为了解决我的具体问题,当记录输入全部为IS NULL
时,我该怎样做才能确保我的函数不被调用?
最后一点 - 我明白如果条目是混合的,那么记录是否为空有一些含糊不清 - 有些NULL
,有些不是。NULL
。但幸运的是,我不必处理这种情况,因为我用作输入的表中的所有列都是NOT NULL
。因此,无论何时调用我的函数,记录都包含所有空值或所有非空值。
答案 0 :(得分:0)
当您使用public function stopAction($campaignId)
{
return new Response('Process Stoped');
}
参数调用A
函数时,会在行的级别进行检查:是作为参数传递的行还是STRICT
?不检查行的内容。解决方案是你应该检查函数开头记录中任何字段的值,record
if NULL
,否则处理函数的其余部分。
答案 1 :(得分:0)
转过来使用nullif
来传递记录时显示null
:
select rec_func(nullif(test_table, (null,null)::test_table))
from test_table