F.15. intarray

intarrayモジュールは整数の一次元配列の操作に便利な関数と演算子を多く提供します。 また、一部の演算子を使用したインデックス検索をサポートします。

F.15.1. intarrayの関数および演算子

表 F-7. intarray関数

関数戻り値の型説明結果
icount(int[])int配列内の要素数icount('{1,2,3}'::int[])3
sort(int[], text dir)int[]配列のソート。dirascまたはdescのいずれかでなければなりません。sort('{1,2,3}'::int[], 'desc'){3,2,1}
sort(int[])int[]昇順ソートsort(array[11,77,44]){11,44,77}
sort_asc(int[])int[]昇順ソート
sort_desc(int[])int[]降順ソート
uniq(int[])int[]隣接する重複を削除uniq(sort('{1,2,3,2,1}'::int[])){1,2,3}
idx(int[], int item)intitemに一致する要素番号(存在しなければ0)idx(array[11,22,33,22,11], 22)2
subarray(int[], int start, int len)int[]startから始まるlen要素分の部分配列subarray('{1,2,3,2,1}'::int[], 2, 3){2,3,2}
subarray(int[], int start)int[]startから始まる部分配列subarray('{1,2,3,2,1}'::int[], 2){2,3,2,1}
intset(int)int[]単一要素の配列を作成intset(42){42}

表 F-8. intarray演算子

演算子戻り値説明
int[] && int[]boolean重なり。配列間で少なくとも1つの共通要素がある場合trueを返します。
int[] @> int[]boolean含有。左辺の配列が右辺の配列を含む場合trueを返します。
int[] <@ int[]boolean含有される。左辺の配列が右辺の配列に含まれる場合trueを返します。
# int[]int配列内の要素数
int[] # intintインデックス(idx関数と同じです)
int[] + intint[]配列に要素をプッシュ(配列の末尾に追加)します
int[] + int[] int[]配列を連結(右辺配列を左辺配列の末尾に追加)します
int[] - intint[]配列から右辺の引数に一致する項目を削除します
int[] - int[]int[]左辺の配列から右辺の配列要素を削除します
int[] | intint[]引数をまとめます
int[] | int[]int[]配列をまとめます
int[] & int[]int[]配列の共通部分
int[] @@ query_intboolean配列が問い合わせを満たす場合true(後述)
query_int ~~ int[]boolean配列が問い合わせを満たす場合true@@の交代演算子)

(PostgreSQL 8.2より前では、含有演算子@>および<@はそれぞれ@および~と呼ばれていました。 これらの名称もまだ使用できますが、廃止予定であり、最終的にはなくなります。 古い名前はコアの幾何データ型が従う規約とは反対であることに注意してください。)

含有演算子@><@は、これらが整数配列のみに動作する点を除き、同名の任意の配列型に対する組み込み演算子と概ね等価です。 重要な違いは、intarrayの演算子は空の配列を何か他のものを含むものとみなさないことです。 これはGINインデックスを使用した問い合わせの動作とは一貫性がありますが、通常の算術的な含有定義とは異なります。

@@および~~演算子は、配列が特化したデータ型query_intで表現される問い合わせを満たすかどうかを試験します。 問い合わせは、おそらく&(論理積), | (論理和), and ! (否定)演算子を組み合わせて使用した、配列要素に対して検査される整数値からなります。 例えば1&(2|3)という問い合わせは1および、2か3のいずれかを含む配列に一致します。

F.15.2. インデックスサポート

intarray&&@><@@@演算子に関して通常の配列等価性と同様にインデックスサポートを提供します。

2つのGiSTインデックス演算子クラスが提供されます。 gist__int_ops(デフォルトで使用されます)は小中規模要素数のデータセット(つまり、異なった配列値を多数持つ列)に適します。一方、 gist__intbig_opsはより大きな署名を使用しますので、大規模データセット(つまり、異なった配列値を多数持つ列)のインデックスにより適しています。 実装は組込みの非可逆圧縮を持ったRD Treeデータ構造を使用します。

また、同じ演算子をサポートするデフォルトではないGIN演算子クラスgin__int_opsも存在します。

GiSTおよびGINインデックスのどちらを選択するかは、別途説明されるGiSTとGINの相対的な性能特徴に依存します。 まとめると、GINインデックスはGiSTインデックスより高速に検索することができますが、構築または更新は低速です。 このため、GINは静的データに適し、GiSTは頻繁に更新されるデータに適します。

F.15.3. 例

-- a message can be in one or more "sections"
CREATE TABLE message (mid INT PRIMARY KEY, sections INT[], ...);

-- create specialized index
CREATE INDEX message_rdtree_idx ON message USING GIST (sections gist__int_ops);

-- select messages in section 1 OR 2 - OVERLAP operator
SELECT message.mid FROM message WHERE message.sections && '{1,2}';

-- select messages in sections 1 AND 2 - CONTAINS operator
SELECT message.mid FROM message WHERE message.sections @> '{1,2}';

-- the same, using QUERY operator
SELECT message.mid FROM message WHERE message.sections @@ '1&2'::query_int;
  

F.15.4. ベンチマーク

ソースディレクトリ以下のcontrib/intarray/benchにはベンチマーク試験一式があります。 以下のように実行します。

   cd .../bench
   createdb TEST
   psql TEST < ../_int.sql
   ./create_test.pl | psql TEST
   ./bench.pl
  

bench.plスクリプトには多くのオプションがあります。 これらは引数を付けずに実行すると表示されます。

F.15.5. 作者

Teodor Sigaev ()とOleg Bartunov ()によりすべての作業がなされました。 さらなる情報についてはhttp://www.sai.msu.su/~megera/postgres/gistを参照してください。 Andrey Oktyabrskiは新しい関数、演算子の追加において素晴らしい作業を行いました。