2

pl/pgsqlで配列をマージ/結合する方法は?

たとえば{1,2,3}、 、{"a","b","c"}、およびの 3 つの配列があります。{32,43,23}

マージした後、次を取得する必要があります。

{{1,"a",32}, {2,"b",43}, {3,"c",23}}

私のPostgreSQLのバージョンは9.0です

4

1 に答える 1

4

zip一部の関数型言語や関数型拡張機能を備えた言語に見られるように、n 引数関数が必要なようです。

この場合、これらの配列は異質な型であるため、あなたが望むことを正確に行うことはできません。PostgreSQL 配列は同種型でなければならないため、これは機能しません。表示する望ましい結果は無効な配列です。

s (匿名レコード) の配列を作成するROWか、すべての値を にキャストできますtext

例えば:

SELECT array_agg(ROW(a,b,c)) 
FROM (
  SELECT 
    unnest('{1,2,3}'::integer[]),
    unnest('{"a","b","c"}'::text[]),
    unnest('{32,43,23}'::integer[])
)
x(a,b,c);

生成されます:

{"(1,a,32)","(2,b,43)","(3,c,23)"}

これは、テキストにキャストされた 3 つの行タイプの配列です。Pg は匿名レコードのサポートが非常に限られているため、扱いにくいでしょう。最も重要なことは、この場合、テキスト値を にキャストできないことです。RECORD(integer,text,integer)実際CREATE TYPEに、定義された型にキャストする必要があります。

その制限のため、代わりにすべての値を にキャストしてtext、 の 2 次元配列を使用することができtextます。単純な でそれができることを期待するでしょうがarray_agg、イライラすることにこれは失敗します:

SELECT array_agg(ARRAY[a::text,b,c::text]) 
FROM (
  SELECT 
    unnest('{1,2,3}'::integer[]),
    unnest('{"a","b","c"}'::text[]),
    unnest('{32,43,23}'::integer[])
)
x(a,b,c);

生産:

ERROR:  could not find array type for data type text[]

array_agg入力として配列をサポートしていないためです。入力を受け取る別のバリ​​アントを定義する必要がありarray_aggますtext[]。少し前に書きましたが、今は見つかりません。探して見つけたら更新しようと思います。textそれまでの間、内部配列を次のようにキャストすることで回避できます。

SELECT array_agg(ARRAY[a::text,b,c::text]::text) 
    FROM (
      SELECT 
        unnest('{1,2,3}'::integer[]),
        unnest('{"a","b","c"}'::text[]),
        unnest('{32,43,23}'::integer[])
    )
    x(a,b,c);

次のような出力を生成します。

 {"{1,a,32}","{2,b,43}","{3,c,23}"}

...OK、私が書いたものは見つかりませんでしたが、これはErwinの例で、うまく機能します。これを試して:

CREATE AGGREGATE array_agg_mult (anyarray)  (
    SFUNC     = array_cat
   ,STYPE     = anyarray
   ,INITCOND  = '{}'
);

SELECT array_agg_mult(ARRAY[ARRAY[a::text,b,c::text]]) 
FROM (
  SELECT 
    unnest('{1,2,3}'::integer[]),
    unnest('{"a","b","c"}'::text[]),
    unnest('{32,43,23}'::integer[])
)
x(a,b,c);

出力:

 {{1,a,32},{2,b,43},{3,c,23}}
于 2013-01-04T02:10:01.470 に答える