class 的自类型注释具有更高的类型
Self-type annotation for class with higher kinded type
给定:
abstract class Databases[F[_]]
我怎样才能使这个特性发挥作用:
// Marker trait signalling the database plugin supports StaticRoles
trait StaticRoles { this: Databases[_] => }
我想确保 StaticRoles
只混入 类 中也扩展了 Databases
,但是我不关心类型参数 [=] 的具体值19=].
代码returns:
error: _ takes no type parameters, expected: one
这很公平,但是 returns 同样的错误:
trait StaticRoles { this: Databases[_[_]] => }
我也试过:
trait StaticRoles { this: Databases[({type T[X[_]]})#T] => }
给出错误:
error: kinds of the type arguments (AnyRef{type T[X[_]]}#T) do not conform to the expected kinds of the type parameters (type F) in class Databases.
AnyRef{type T[X[_]]}#T's type parameters do not match type F's expected parameters:
type X has one type parameter, but type _ has none
我认为你应该定义如下:
abstract class Databases[F[_]]
trait StaticRoles[F[_]] { this: Databases[F] =>
def abc: String
}
class Abc extends Databases[IO] with StaticRoles[IO] {
override def abc: String = ???
}
注意:如果你删除Databases[IO]
并且只是像这样定义
class Abc extends StaticRoles[IO] {...}
这不会编译。我认为这就是你想要实现的目标
正确的是
trait StaticRoles { this: (Databases[F] forSome { type F[_] }) => }
并非所有存在类型都可以用下划线表示或(在本例中)允许用下划线表示。
还有
trait StaticRoles { this: Databases[F forSome { type F[_] }] => }
与前者不同但与前者相同
trait StaticRoles { this: Databases[Any] => }
从
implicitly[(Databases[F forSome { type F[_] }]) =:= Databases[Any]]
(Any
其实是多亲的).
Databases[Any]
是 Databases[F] forSome { type F[_] }
的子类型
implicitly[Databases[Any] <:< (Databases[F] forSome { type F[_] })]
使用类型投影 (#
) 正确的是
trait StaticRoles { this: Databases[({ type F[_] })#F] => }
Databases[({ type F[_] })#F]
也是 Databases[F] forSome { type F[_] }
的子类型(对于不变的 Databases
,与 Databases[Any]
无法比较)。
在 Databases[F] forSome { type F[_] }
、Databases[Any]
和 Databases[({ type F[_] })#F]
这三种类型中,只有第一种适用于
trait IO[_]
class Abc extends Databases[IO] with StaticRoles // compiles
//class Abc1 extends StaticRoles // doesn't compile
给定:
abstract class Databases[F[_]]
我怎样才能使这个特性发挥作用:
// Marker trait signalling the database plugin supports StaticRoles
trait StaticRoles { this: Databases[_] => }
我想确保 StaticRoles
只混入 类 中也扩展了 Databases
,但是我不关心类型参数 [=] 的具体值19=].
代码returns:
error: _ takes no type parameters, expected: one
这很公平,但是 returns 同样的错误:
trait StaticRoles { this: Databases[_[_]] => }
我也试过:
trait StaticRoles { this: Databases[({type T[X[_]]})#T] => }
给出错误:
error: kinds of the type arguments (AnyRef{type T[X[_]]}#T) do not conform to the expected kinds of the type parameters (type F) in class Databases.
AnyRef{type T[X[_]]}#T's type parameters do not match type F's expected parameters:
type X has one type parameter, but type _ has none
我认为你应该定义如下:
abstract class Databases[F[_]]
trait StaticRoles[F[_]] { this: Databases[F] =>
def abc: String
}
class Abc extends Databases[IO] with StaticRoles[IO] {
override def abc: String = ???
}
注意:如果你删除Databases[IO]
并且只是像这样定义
class Abc extends StaticRoles[IO] {...}
这不会编译。我认为这就是你想要实现的目标
正确的是
trait StaticRoles { this: (Databases[F] forSome { type F[_] }) => }
并非所有存在类型都可以用下划线表示或(在本例中)允许用下划线表示。
还有
trait StaticRoles { this: Databases[F forSome { type F[_] }] => }
与前者不同但与前者相同
trait StaticRoles { this: Databases[Any] => }
从
implicitly[(Databases[F forSome { type F[_] }]) =:= Databases[Any]]
(Any
其实是多亲的).
Databases[Any]
是 Databases[F] forSome { type F[_] }
implicitly[Databases[Any] <:< (Databases[F] forSome { type F[_] })]
使用类型投影 (#
) 正确的是
trait StaticRoles { this: Databases[({ type F[_] })#F] => }
Databases[({ type F[_] })#F]
也是 Databases[F] forSome { type F[_] }
的子类型(对于不变的 Databases
,与 Databases[Any]
无法比较)。
在 Databases[F] forSome { type F[_] }
、Databases[Any]
和 Databases[({ type F[_] })#F]
这三种类型中,只有第一种适用于
trait IO[_]
class Abc extends Databases[IO] with StaticRoles // compiles
//class Abc1 extends StaticRoles // doesn't compile