【发布时间】:2020-05-02 19:28:41
【问题描述】:
我正在尝试编写一个 plpgsql 程序来执行 postGIS 表的空间平铺。我可以使用以下对表名进行硬编码的过程成功执行该操作。该过程循环遍历 tile_table 中的图块,并为每个图块剪切 area_table 并将其插入 split_table。
CREATE OR REPLACE PROCEDURE splitbytile()
AS $$
DECLARE
tile RECORD;
BEGIN
FOR tile IN
SELECT tid, geom FROM test_tiles ORDER BY tid
LOOP
INSERT INTO split_table (id, areaname, ttid, geom)
SELECT id, areaname, tile.tid,
CASE WHEN st_within(base.geom, tile.geom) THEN st_multi(base.geom)
ELSE st_multi(st_intersection(base.geom, tile.geom)) END as geom
FROM area_table as base
WHERE st_intersects(base.geom, tile.geom);
COMMIT;
END LOOP;
END;
$$ LANGUAGE 'plpgsql';
已经成功测试了这个,现在我需要将它转换为一个动态过程,我可以在其中提供表名作为参数。我尝试了以下部分转换,在循环内部使用 format():
CREATE OR REPLACE PROCEDURE splitbytile(in_table text, grid_table text, split_table text)
AS $$
DECLARE
tile RECORD;
BEGIN
FOR tile IN
EXECUTE format('SELECT tid, geom FROM %I ORDER BY tid', grid_table)
LOOP
EXECUTE
FORMAT(
'INSERT INTO %1$I (id, areaname, ttid, geom)
SELECT id, areaname, tile.tid,
CASE WHEN st_within(base.geom, tile.geom) THEN st_multi(base.geom)
ELSE st_multi(st_intersection(base.geom, tile.geom)) END as geom
FROM %2$I as base
WHERE st_intersects(base.geom, tile.geom)', split_table, in_table
);
COMMIT;
END LOOP;
END;
$$ LANGUAGE 'plpgsql';
但是会报错
missing FROM-clause entry for table "tile"
那么,如何将程序转换为动态程序?更具体地说,如何在循环内使用 for 循环返回的记录数据类型(平铺)?请注意,它在不使用格式时有效。
【问题讨论】:
标签: postgresql postgis plpgsql