受正确类型限制的类型构造函数

Mar*_*lic 2 generics scala type-constraints higher-kinded-types type-constructor

请看下面的类型参数子句[F[_] <: Int]中

def h[F[_] <: Int] = ???
Run Code Online (Sandbox Code Playgroud)

其中类型构造函数F受正确类型的限制Int。现在,这两个h[List]和h[Int]是非法的

scala> def h[F[_] <: Int] = ???
     |
def h[F[_] <: Int]: Nothing

scala> h[List]
        ^
       error: type arguments [List] do not conform to method h's type parameter bounds [F[_] <: Int]

scala> h[Int]
         ^
       error: Int takes no type parameters, expected: 1
Run Code Online (Sandbox Code Playgroud)

那么为什么是[F[_] <: Int]合法的呢?

HTN*_*TNW 5

类型参数声明F[_] <: Int意味着每个 的实例化都F必须是 的子类型Int。它在语法上是正确的,虽然很神秘:F不必是Int;的子类型。F[_]必须是 的子类型Int(对于可能放在 中的所有类型_)。这种情况的一个例子F是总是返回Int:

type ConstInt[X] = Int
h[ConstInt] // compiles
Run Code Online (Sandbox Code Playgroud)

请注意,您可以在_. 例如,我可以声明一个类型参数F[X] <: X。X对声明来说是局部的,定义为出现在F左边,用作右边的边界,然后超出范围。此示例意味着F[X]必须是 的子类型X,例如

def f[F[X] <: X] = ???
type Identity[X] = X
f[Identity] // works
type ConstNothing[X] = Nothing
f[ConstNothing] // works
// f[ConstInt] (ConstInt[X] = Int is not always a subtype of X; counterexample X = AnyRef)
Run Code Online (Sandbox Code Playgroud)

也许这让我们明白了界限应该意味着什么。