Postgresql 函数在表中插入多行

Postgresql 函数在表中插入多行,postgresql,postgresql-9.1,postgresql-9.2,postgresql-9.5,Postgresql,Postgresql 9.1,Postgresql 9.2,Postgresql 9.5,因此,我有以下表格 G __________________________ id_musician | id_album -------------------------- 1 | 51 3 | 52 2 | 53 3 | 54 1 | 55 3 | 56 C ___

因此,我有以下表格

             G
__________________________
id_musician  |    id_album
--------------------------
1            |    51
3            |    52
2            |    53
3            |    54
1            |    55
3            |    56

            C
__________________________
id_album    |      year
--------------------------
51          |    1990
52          |    2001
53          |    1990
54          |    2001
55          |    1945
56          |    1945
我创建了以下函数:

CREATE OR REPLACE FUNCTION test2 (year1 INTEGER, p_type VARCHAR(1))
RETURNS SETOF test2 AS $$
DECLARE
output test2;
BEGIN
IF p_type='S' THEN
FOR output IN SELECT g.id_artist, c.year, COUNT(c.id_album) AS albums
FROM G g, C c
WHERE g.id_album = c.id_album AND
c.year = year1
GROUP BY c.year, g.id_musician
LOOP
RETURN NEXT output;
END LOOP;
END IF
RETURN;
END;
$$LANGUAGE plpgsql;
CREATE OR REPLACE FUNCTION test2 (year1 INTEGER, p_type VARCHAR(1))
    RETURNS SETOF test2 AS
$BODY$
BEGIN
    IF p_type='S' THEN
        RETURN QUERY (
            WITH inserted AS (
                INSERT INTO test2_table
                SELECT g.id_musician, c.year, COUNT(c.id_album)::INTEGER AS albums
                FROM g, c
                WHERE g.id_album = c.id_album
                AND c.year = year1
                GROUP BY c.year, g.id_musician
                RETURNING *
            )
            SELECT *
            FROM inserted
        );
    ELSE
        RETURN;
    END IF;
END
$BODY$
    LANGUAGE plpgsql;
test2是我创建的一种输出类型:

CREATE TYPE test2 AS(
        id smallint,
        year smallint,
        total_albums integer)
该函数接受一年和一种performer。它返回,对于每一年和表演者(在本例中是吉他手“G”),表演者每年参与的唱片数量

我希望函数将该输出插入到我创建的表中,而不仅仅是显示输出:

CREATE TABLE TEST2_TABLE (
id smallint,
year smallint,
total_albums integer );
下面是函数:

CREATE OR REPLACE FUNCTION test2 (year1 INTEGER, p_type VARCHAR(1))
RETURNS SETOF test2 AS $$
DECLARE
output test2;
BEGIN
IF p_type='S' THEN
FOR output IN SELECT g.id_artist, c.year, COUNT(c.id_album) AS albums
FROM G g, C c
WHERE g.id_album = c.id_album AND
c.year = year1
GROUP BY c.year, g.id_musician
LOOP
RETURN NEXT output;
END LOOP;
END IF
RETURN;
END;
$$LANGUAGE plpgsql;
CREATE OR REPLACE FUNCTION test2 (year1 INTEGER, p_type VARCHAR(1))
    RETURNS SETOF test2 AS
$BODY$
BEGIN
    IF p_type='S' THEN
        RETURN QUERY (
            WITH inserted AS (
                INSERT INTO test2_table
                SELECT g.id_musician, c.year, COUNT(c.id_album)::INTEGER AS albums
                FROM g, c
                WHERE g.id_album = c.id_album
                AND c.year = year1
                GROUP BY c.year, g.id_musician
                RETURNING *
            )
            SELECT *
            FROM inserted
        );
    ELSE
        RETURN;
    END IF;
END
$BODY$
    LANGUAGE plpgsql;
因此,签名和输出与原始函数相同。主要区别是:

  • 无需使用循环并一次读取/返回一行。您可以直接返回查询结果。像那样快得多
  • 为了完成插入到表中和返回相同的结果,它使用一个CTE将数据插入表中并返回插入的所有内容,然后从该CTE中选择作为返回输出

我还删除了别名。postgres中的任何标识符都是小写的,除非使用双引号。由于
G
C
不在引号中,因此表名实际上分别是
G
C
。因此,我只使用了实际的小写表名。

“将该输出插入到我创建的表中”,您没有向我们显示该表,而是重新发布了类型定义。那么您希望它将输出写入表并返回它,还是只是写入它?对不起,这是一个错误,我现在已经更正了。该表为空,理想情况下,它将返回类型并将其插入到表TEST2\u表中。然而,如果这不可能,我会满足于只填充表格的函数