在编程语言理论中,子类型(动名词,英語:subtyping)是一种类型多态的形式。这种形式下,子类型(名词,英語:subtype)可以替换另一种相关的数据类型(超类型,英語:supertype)。也就是说,针对超类型元素进行操作的子程序、函数等程序元素,也可以操作相应的子类型。如果 S 是 T 的子类型,这种子类型关系通常写作 S <: T,意思是在任何需要使用 T 类型对象的环境中,都可以安全地使用 S 类型的对象。子类型的准确语义取决于具体的编程语言中「X 环境中,可以安全地使用 Y」的意义。编程语言的类型系统定义了各自不同的子类型关系。
在多数基于类的面向对象编程语言中,子类引出子类型:如果 A 是 B 的子类,则类 A 的实例可以用在期望类 B 的实例的任何上下文中;所以我们称 A 是 B 的子类型。一个结论就是声明有类型 B 的任何变量或形式参数在运行时间可以持有类 A 的一个值;在这种情况下很多面向对象编程者会声称 B 是这个变量的“静态类型”而 A 是它的“动态类型”。这个规则的例外包括 C++语言中的私有继承(它不建立子类型),和 Eiffel 语言中在派生类型上特定运算,在其中继承自基类的特征可以用违反子类型规则的方式去除或修改。
另一个例子是可以允许整数值被用在期望浮点数值的地方,或可以定义包含整数和实数二者的一个类型 number 的语言。在第一种情况下,整数类型将是浮点数类型的子类型;在第二种情况下,这两个类型都是 number 的子类型而相互之间无子类型关系。
编程者可利用子类型来以比没有它更抽象的方式来写代码。考虑下面的例子:
function max (x as number, y as number) is
if x < y then
return y
else
return x
end
如果整数和实数都是 number 的子类型,则二者任何类型都可以传递给这个函数。为此,子类型经常被认为是一种形式的多态性。上述例子也可以比较于 C++ 语言的模板。
在类型论中,子类型关系经常写为 <:,有着 A<:B 意味着 A 是 B 的子类型。在类型论中子类型可用如下事实来特征化,如果 A<:B,类型 A 的任何表达式也可被给予类型 B;立法这个特征化的形式类型规则叫做“包容”规则。