PostgreSQLのデータ型は、基本型、複合型、ドメイン、疑似型に分類されます。
基本型はint4のように、SQL言語レベル以下で実装されたものです (通常はCのような低レベル言語で作成されます)。 一般的にこれらは抽象データ型とも呼ばれるものに対応します。 PostgreSQLは、ユーザによって提供された関数を通して、こうした型に対する操作のみが可能です。 そして、こうした型の動作のみをユーザが記述する範囲まで理解することができます。 さらに基本型は、スカラと配列型に分類されます。 各スカラ型に対応する配列型は自動的に作成され、そこにはそのスカラ型の可変長の配列を保持できます。
ユーザがテーブルを作成すると、複合型、もしくは行型が作成されます。関連するテーブルを持たない"スタンドアロン"の複合型をCREATE TYPEを使用して定義することもできます。複合型は関連したフィールド名を持つ基本型の単なるリストです。複合型の値は、行もしくはフィールド値のレコードです。ユーザはSQL問い合わせによってその構成フィールドにアクセスすることができます。複合型のより詳細は項8.15を参照してください。
ドメインは、特定の基本型に基づいたもので、多くの目的では、その基本型と交換可能です。 しかし、ドメインは背後にある基本型で許可される範囲内で値の有効範囲を制限する制約を持つことができます。
ドメインはCREATE DOMAIN SQLコマンドを使用して作成可能です。 ドメインの作成と使用については本章では説明しません。
特殊な目的用に数個の"疑似型"があります。 疑似型はテーブルの列や複合型の属性として現れることはありません。 しかし、関数の引数や結果型を宣言する際に使用することができます。 これは、型システム内で特殊な関数クラスを識別するための機構を提供します。 表8-20に既存の疑似型を列挙します。
特殊な用途を持つ疑似型には、anyelementとanyarray、anynonarray、およびanyenumの4つがあります。 これらはまとめて多様型と呼ばれます。 これらの型を使用すると宣言された関数は全て、多様関数と呼ばれます。 多様関数は多くの異なるデータ型を操作することができます。 データ型の指定は、特定の呼び出しに実際に渡されるデータ型によって決定されます。
多様引数と結果は互いに結び付いており、多様関数を呼び出す問い合わせが解析される時に特定のデータ型が決定されます。 anyelementとして宣言された位置(引数もしくは戻り値)にはそれぞれ、任意の実データ型を指定することができますが、1つの呼び出しでは、これら全ては同一の実データ型でなければなりません。 anyarrayとして宣言された位置には、任意の配列データ型を持つことができます。 しかし、同様にこれらは全て同じデータ型でなければなりません。 anyarrayと宣言された位置とanyelementと宣言された位置の両方がある場合、anyarrayの位置の実際の配列型は、その要素の型がanyelement位置に現れる型と同じでなければなりません。 anynonarrayは、実際の型が配列型であってはならないという制限が加わっている点を除き、anyelementとまったく同様に扱われます。 anyenumは、実際の型が列挙型でなければならないという制約が加わっている点を除き、anyelementとまったく同様に扱われます。
このように、1つ以上の引数位置が多様型と宣言されると、全体の効果として、実引数型の特定の組み合わせのみが許されるようになります。 例えば、equal(anyelement, anyelement)と宣言された関数は、2つの引数が同じデータ型である限り、任意の入力値を2つ取ることになります。
関数の戻り値を多様型として宣言する時、少なくとも1つの引数位置も多様でなければなりません。 そして引数として与えられる実データ型がその呼び出しの実結果型を決定します。 例えば、配列添字機構がなかったとすると、subscript(anyarray, integer) returns anyelementとして添字機構を実装する関数を定義できます。 この宣言には、最初の実引数は配列型になり、パーサはこの最初の実引数の型より正しい結果型を推論することができます。 他にもたとえば、f(anyarray) returns anyenumと宣言された関数は列挙型の配列のみを受け付けます。
anynonarray型とanyenum型が、別個の型変数を表していないことに注意してください。 これはanyelementと同じ型で、追加の制約が付いているだけです。 たとえば、f(anyelement, anyenum)として関数を宣言することは、f(anyenum, anyenum)と宣言することと同一です。 両方の実引数は同じ列挙型でなければなりません。