使用更高种类的类型参数时,了解类型参数不符合类类型参数界限错误 [英] Understanding type arguments do not conform to class type parameter bounds error when using Higher kinded type parameter

查看:63
本文介绍了使用更高种类的类型参数时,了解类型参数不符合类类型参数界限错误的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我试图理解为什么当我在MyModel中为T使用更高种类的类型参数时,下面的代码为何无法编译

I am trying to understand why the following piece of code won't compile when I use a higher kinded type parameter for T in MyModel

abstract class Model[M <: Model[M]]

class MyModel[T] extends Model[MyModel[T]]

class Bar[TModel <: Model[TModel]]

object Foo extends App {

  new Bar[MyModel[_]]

}

但是如果我将其更改为 new Bar [MyModel [Any]] ,它将进行编译.为什么会这样?

But if i change it to new Bar[MyModel[Any]] it will compile. Why is this ?

推荐答案

Bar [MyModel [_]] ((既不应与 Bar [MyModel [X]] forSome {type X} 混淆,也不应与 Bar [MyModel [X forSome {type X}]] 混淆)>,后者只是 Bar [MyModel [Any]] .这是三种不同的类型.)

(It should not be confused neither with Bar[MyModel[X]] forSome {type X} nor with Bar[MyModel[X forSome {type X}]], the latter is just Bar[MyModel[Any]]. These are three different types.)

Bar [MyModel [X] forSome {type X}] (又名 Bar [MyModel [_]] )未编译,因为 MyModel [X] forSome {type X} (又名 MyModel [_] )不满足 Bar 的条件 TModel< ;: Model [TModel].实际上,您可以检查

Bar[MyModel[X] forSome {type X}] (aka Bar[MyModel[_]]) doesn't compile because MyModel[X] forSome {type X} (aka MyModel[_]) doesn't satisfy Bar's condition TModel <: Model[TModel]. Indeed you can check that

implicitly[(MyModel[X] forSome {type X}) <:< Model[MyModel[X] forSome {type X}]]

不会编译( X <:< 的左边,而 X <:< 不相关).这是上存在类型的"https://scala-lang.org/files/archive/spec/2.13/03-types.html#existential-types" rel ="nofollow noreferrer">伪造MyModel [X] forSome {type X} ,即 MyModel [X1] 未连接到 Model [MyModel [X] forSome {type X}] 右边,对于不变的 Model (来自 class MyModel [T]扩展了Model [MyModel [T]] ,它遵循 MyModel [X1]< ;: Model [MyModel [X1]] (1),也 MyModel [X1]< ::(MyModel [X] forSome {type X})(2),但对于不变的 Model我们不能将 Model 应用于后者的不平等").

doesn't compile (X to the left from <:< and X to the right from <:< are not related). The thing is that skolemization of existential type on the left MyModel[X] forSome {type X}, namely MyModel[X1] is not connected to Model[MyModel[X] forSome {type X}] on the right, for invariant Model (from class MyModel[T] extends Model[MyModel[T]] it follows that MyModel[X1] <: Model[MyModel[X1]] (1), also MyModel[X1] <: (MyModel[X] forSome {type X}) (2), but for invariant Model we can't apply Model to the latter "inequality").

但是,如果您使 Model 协变抽象类Model [+ M< ;: Model [M]] ,那么我们可以将 Model 应用于不等式"(2),因此 Model [MyModel [X1]]< ;: Model [MyModel [X] forSome {type X}] ,并将此与(1)一起给出 MyModel [X1]< ;:通过传递性实现Model [MyModel [X] forSome {type X}] .这样就满足了 Bar 的条件,并编译了 new Bar [MyModel [_]] .

But if you make Model covariant abstract class Model[+M <: Model[M]] then we can apply Model to "inequality" (2), so Model[MyModel[X1]] <: Model[MyModel[X] forSome {type X}] and this along with (1) gives MyModel[X1] <: Model[MyModel[X] forSome {type X}] by transitivity. So Bar's condition is satisfied and new Bar[MyModel[_]] compiles.

Bar [MyModel [Any]] 编译是因为 MyModel [Any] 满足 Bar 的条件 TModel< ;:模型[TModel] .确实是 MyModel [Any]< ;: Model [MyModel [Any]] ,因为 class MyModel [T]扩展了Model [MyModel [T]] (您可以检查

Bar[MyModel[Any]] compiles because MyModel[Any] satisfies Bar's condition TModel <: Model[TModel]. Indeed MyModel[Any] <: Model[MyModel[Any]] because class MyModel[T] extends Model[MyModel[T]] (you can check that

implicitly[MyModel[Any] <:< Model[MyModel[Any]]]

编译).

这篇关于使用更高种类的类型参数时,了解类型参数不符合类类型参数界限错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆