サブタイピング()や部分型とは、型のポリモーフィズムの形態であり、上位と定義された型を、その下位と定義された型で、型安全性に則って代替できるというの概念および実装を意味している。

スーパータイプは、そのサブタイプの数々によって代替/代入可能とされており、これは代入可能性(substitutability)と呼ばれる。そのスーパータイプとサブタイプの関係は、is-aとも言われる。記号<:を用いてsubtype <: supertypeと表記される。

スーパータイプ+サブタイプの概念はその時の用法で、上位型(supertype)+下位型(subtype)、基底型(base type)+派生型(derived type)、基本型(basic type)+拡張型(extend type)、上位型(supertype)+部分型(subtype) などの別称に使い分けられており、それぞれの性質にも差異がある。

起源 サブタイピング(subtyping)は、Simula67で登場した継承と仮想手続き(仮想関数)を分析した計算機科学者によって1980年に考案された言葉である。それを更に研究したらが、1985年にインクルージョン多相という概念にまとめた。

サブタイピングは、型理論ではなく、オブジェクト指向言語の継承とメソッドオーバーライドによるのポリモーフィズムを由来にしている。1994年にバーバラ・リスコフが、オブジェクト指向の継承のサブタイピング用法を重視したリスコフの置換原則を提唱している。サブタイピングは上位概念と下位概念(hypernymy・hyponymy)に言及されることがあり、。

サブタイピングに関連付けられているその他の概念としては、発のインターフェース、ジェネリックプログラミングの総称型、部分構造論理由来のなどがある。サブタイピングを型理論視点で解釈拡張したものにがある。

関数型言語の型構築子には深さサブタイピング(depth subtyping)という別解釈が加えられている。関数型言語はレコード型の深さサブタイピングと幅サブタイピング(width subtyping)や、の共変反変サブタイピングも取り入れている。

例 サムネイル|300x300ピクセル|UMLクラス図表現。トリは基底型。アヒル・カッコウ・ダチョウは派生型。 最初の例は、UMLクラス図のスーパークラスとサブクラスのサブタイピングである(右図参照)。ここでのsupertypeは基底型、subtypeは派生型と呼ばれやすい。

トリは基底型であり、アヒル/カッコウ/ダチョウは派生型である。トリ型の変数xには、トリ型のインスタンスだけでなく、アヒル/カッコウ/ダチョウ型のインスタンスをも代入できて、その際の変数xは、トリ型の派生(sub)で型付け(typing)されることになる。

二番目の例は、型の上位概念と下位概念に基づいた変数である。ここではsupertypeは上位型、subtypeは下位型と呼ばれやすい。

それぞれ数値型のNumber(総称的な数値)Float(浮動小数点)Integer(整数)があるとして、これらはサブタイプ記号<:でこのように表現できる。

Integer <: Float <: Number Integer <: Number と Float <: Number

上の規則によって、Number型の変数xに、Float型とInteger型の値を代入できることになる。従って変数xは多相になる。

そのコード例はこのようになる。

function max (x as Number, y as Number) if x < y then return y else return x end

関数maxは、Number型の引数x,yを通して、Float値とInteger値を計算できる。その際の引数x,yは、Number型の下位(sub)で型付け(typing)されることになる。

性質 型理論においては、部分型関係は <: と表記される。つまり、A <: B という表記は A は B の部分型であるという意味である。型理論における部分型は、A <: B ならば型 A を持つ式はどれでも型 B をも持つという事実によって特性付けられる。この形式的な推論規則は包摂(subsumption)として知られている。

型理論の研究者は、部分型であると宣言されたもののみを部分型とすると、2つの型の構造によって部分型関係にあるかが決まるを区別する。上記のクラスベースオブジェクト指向言語の例は名前的型システムである。構造的型システムのオブジェクト指向言語では、型 のオブジェクトが型 のオブジェクトの処理できるメッセージすべてを処理できるなら(言い換えると、同じメソッドを実装していれば)、継承関係に関係なく、 は の部分型となる。

部分型を持つプログラミング言語の実装は大きく2つに分類される。型 の値の内部表現が型 の値としての内部表現も兼ねるinclusive(包含的)な実装と、型 の値が型 の値に「自動的に変換」されることのあるcoercive(強制的)な実装である。オブジェクト指向言語のサブクラスによる型の派生はたいてい包含的である。前述の整数と浮動小数点数の派生型関係は、内部表現が異なっているので、強制的な例である。

ほぼすべての型システムでは部分型関係が定義されている。それは反射律(任意の型 について、)と推移律( かつ ならば )を満たすものである。つまり前順序が成り立つ。

関連項目 ポリモーフィズム 継承 オーバーライド スーパークラス・サブクラス インターフェース

参考資料

邦訳『オブジェクト指向入門 第2版』 ISBN 4798111112

参照

外部リンク c2.com: Nominative and structural typing