Skip to content

Bounded quantification

"bounded"的含义是"有界限的","quantification"的含义是"量化"。

"bounded quantification"所描述的是在generic programming中,对parameter进行constrain,从下面的介绍可以看出,它是: generic programming + OOP subtyping。

wikipedia Bounded quantification

In type theory, bounded quantification (also bounded polymorphism or constrained genericity) refers to universal or existential quantifiers which are restricted ("bounded") to range only over the subtypes of a particular type. Bounded quantification is an interaction of parametric polymorphism with subtyping. Bounded quantification has traditionally been studied in the functional setting of System F<:, but is available in modern object-oriented languages supporting parametric polymorphism (generics) such as Java, C# and Scala.

NOTE: 相比之下,constrained genericity 是更加容易理解的,它的字面意思是: 受限的genericity,它能够更加直接地传递出 bounded quantification的含义;

从上面的描述能够看出:

bounded quantification是"parametric polymorphism with subtyping"。

Overview

The purpose of bounded quantification is to allow for polymorphic functions to depend on some specific behaviour of objects instead of type inheritance.

NOTE: behavior-based VS inheritance-based

F-bounded quantification

***F*-bounded quantification** or recursively bounded quantification, introduced in 1989, allows for more precise typing of functions that are applied on recursive types. A recursive type is one that includes a function that uses it as a type for some argument or its return value.[1]

NOTE: C++ CRTP就是典型的F-bounded quantification

Example

This kind of type constraint can be expressed in Java with a generic interface. The following example demonstrates how to describe types that can be compared to each other and use this as typing information in polymorphic functions. The Test.min function uses simple bounded quantification and does not preserve the type of the assigned type

s, in contrast with the Test.Fmin function which uses F-bounded quantification.

interface Comparable<T> {
  public int compareTo(T other);
}

class Integer implements Comparable<Integer> {
  @Override
  public int compareTo(Integer other) {
    //...
  }
}

class String implements Comparable<String> {
  @Override
  public int compareTo(String other) {
    //...
  }
}

class Test {
  public static void main(String[] args) {
    Comparable<String> a = min("cat", "dog");
    Comparable<Integer> b = min(new Integer(10), new Integer(3));
    String str = Fmin("cat", "dog");
    Integer i = Fmin(new Integer(10), new Integer(3));
  }
  public static <S extends Comparable> S min(S a, S b) {
    if (a.compareTo(b) <= 0)
      return a;
    else
      return b;
  }
  public static <T extends Comparable<T>> T Fmin(T a, T b) {
    if (a.compareTo(b) <= 0)
      return a;
    else
      return b;
  }
}