我有一个表(名为VGI_table),其中包含一个列(名为match_tabl),该列包含同一数据库中其他表的名称以及这些表的object_ids。我正在尝试创建一个plpgsql函数,它循环遍历VGI_table中的每一行,并执行查询以从另一个表中检索对象,如下所示。
该函数有4个参数(所有varchar),前两个是VGI_table中的列名,第三个是VGI_table的名称,最后一个参数是输出。
vgi_match_id_col, vgi_match_table_col, vgi_table, output_table
该函数的代码如下所示,ro用于保存第一个表查询,match_row保存查询的外部表的输出。距离是使用PostGIS st_distance函数创建的输出。
DECLARE
ro record;
match_row record;
distance float;
BEGIN
for ro in EXECUTE 'select gid, geom, '||vgi_match_id_col||' as match_id, '||vgi_match_table_col||' as match_table from '||vgi_table
LOOP
--raise notice '(%)', 'select geom from public.'||ro.match_table||' where gid = '||ro.match_id;
execute 'select geom from public.'||ro.match_table||' where gid = '||ro.match_id into match_row;
distance := st_distance(ro.geom, st_transform(match_row.geom,st_srid(ro.geom)));
EXECUTE 'INSERT INTO '||output_table||' VALUES('||ro.gid||', '||distance||')';
END LOOP;
正在查询的表在match_tabl列或object_id列中没有空值。在尝试执行EXECUTE语句时,代码将ro.match_table和ro.match_id标识为空值。我甚至使用RAISE NOTICE函数和EXECUTE语句中使用的相同字符串,并返回正确的查询。如果我使用预定义的table_name和对象id对执行字符串进行硬编码,则脚本可以正常工作。以下链接类似,但我不认为它解决了我的问题。谢谢你的帮助。
答案 0 :(得分:3)
嗯,显然你要连接的东西是空的。
使用server.xml
功能,这样您就可以获得更多有用信息。
format
使用format('select geom from public.%I ....', ro.match_table);
插入文字。
e.g。
EXECUTE ... USING ...
答案 1 :(得分:0)
在postgres中,如果在动态DML中传递了任何null,我们必然会遇到这个问题。“EXECUTE的查询字符串参数为null” 您可以使用以下示例步骤进行插入和更新。
CREATE OR REPLACE FUNCTION samplefunc(
col1param character varying,
col2param character varying,
col3param character varying,
col4param character varying,
col5param character varying,
col6param character varying,
col7param character varying,
col8param character varying
RETURNS boolean AS
$BODY$
declare
begin
EXECUTE format( 'insert into '||tablename||' (id, col1, col2, col3, col4, col5)values($1,$2,$3,$4,$5)') USING col1param ,col2param,col3param,col4param,col5param;
EXECUTE format('update '||tablename||' set col1 =$1,col2 = $2,col3=$3,col4=$4,col5=$5
where col6=$6 and col7=$7 and col8=$8 ') using col1param,col2param,,col3param,col4param,col5param,col6param,col7param,col8param;
end