関数からレコードセット(仮想テーブル)を返す 質問する

関数からレコードセット(仮想テーブル)を返す 質問する

カスタム コンテンツを含む仮想テーブル (Oracle のような) を返す Postgres 関数が必要です。テーブルには 3 つの列と不明な数の行が含まれます。

インターネット上で正しい構文を見つけることができませんでした。

想像してみてください:

CREATE OR REPLACE FUNCTION "public"."storeopeninghours_tostring" (numeric)
  RETURNS setof record AS
DECLARE
  open_id ALIAS FOR $1;
  returnrecords setof record;
BEGIN
  insert into returnrecords('1', '2', '3');
  insert into returnrecords('3', '4', '5');
  insert into returnrecords('3', '4', '5');
  RETURN returnrecords;
END;

これはどのように正しく書かれていますか?

ベストアンサー1

これまでの回答はすべて時代遅れか、そもそも非効率的でした。

3 つの列を返すと仮定しますinteger

PL/pgSQL関数

最新の PL/pgSQL (PostgreSQL 8.4 以降) でこれを行う方法は次のとおりです。

CREATE OR REPLACE FUNCTION f_foo() -- (open_id numeric) -- parameter not used
  RETURNS TABLE (a int, b int, c int) AS
$func$
BEGIN
RETURN QUERY VALUES
  (1,2,3)
, (3,4,5)
, (3,4,5)
;
END
$func$  LANGUAGE plpgsql IMMUTABLE ROWS 3;

Postgres 9.6以降では、以下を追加することもできます。PARALLEL SAFE

電話:

SELECT * FROM f_foo();

主なポイント

  • 使用RETURNS TABLE返されるアドホック行タイプを定義します。
    または、RETURNS SETOF mytbl定義済みの行タイプを使用します。

  • 使用RETURN QUERY1 つのコマンドで複数の行を返します。

  • 使うVALUES複数の行を手動で入力するための式です。これは標準SQLであり、永遠に

  • もし実際にパラメータが必要な場合は、(open_id numeric)代わりにパラメータ名を使用してください。ALIAS、これは推奨されない. この例では、パラメータは使用されず、ノイズだけが使用されました...

  • 完全に正当な識別子を二重引用符で囲む必要はありません。二重引用符は、そうでなければ不正な名前 (大文字と小文字が混在、不正な文字または予約語) を強制する場合にのみ必要です。

  • 関数の変動性はIMMUTABLE結果は決して変わらないからです。

  • ROWS 3はオプションですが、知る返される行数がわからない場合は、それを Postgres に宣言することもできます。これにより、クエリ プランナーが最適なプランを選択するのに役立ちます。

シンプルなSQL

このような単純なケースでは、代わりに単純な SQL ステートメントを使用できます。

VALUES (1,2,3), (3,4,5), (3,4,5)

または、特定の列名と型を定義したい(または定義しなければならない)場合は、次のようにします。

SELECT *
FROM  (
   VALUES (1::int, 2::int, 3::int)
        , (3, 4, 5)
        , (3, 4, 5)
   ) AS t(a, b, c);

SQL関数

シンプルなSQL関数その代わり:

CREATE OR REPLACE FUNCTION f_foo()
   RETURNS TABLE (a int, b int, c int) AS
$func$
   VALUES (1, 2, 3)
        , (3, 4, 5)
        , (3, 4, 5);
$func$  LANGUAGE sql IMMUTABLE ROWS 3;

おすすめ記事