简体   繁体   English

Scala:在继承树的底部放置类型

[英]Scala: Placing type at bottom of inheritance tree

Scala defines a type called Nothing that is a sub-type of all types. Scala定义了一个名为Nothing的类型,它是所有类型的子类型。 Is it possible to define our own "bottom types" that should be at the bottom of an inheritance tree that extends from a given super-type? 是否可以定义我们自己的“底部类型”,它应该位于从给定超类型扩展的继承树的底部?

For example, suppose I have some type Foo , and I want to say Xyzzy should be at the bottom of Foo 's inheritance tree - in other words, it should inherit from anything that inherits from Foo. 例如,假设我有一些类型Foo ,我想说Xyzzy应该位于Foo的继承树的底部 - 换句话说,它应该继承自Foo继承的任何东西。 If we introduce a new type Bar , and Bar <: Foo , then Xyzzy <: Bar . 如果我们介绍一个新类型的Bar ,和Bar <: Foo ,那么Xyzzy <: Bar I'm basically looking for a way to say class Xyzzy isBottom Foo { ... } . 我基本上都在寻找一种方法来说class Xyzzy isBottom Foo { ... } Is there any way to achieve this directly, or indirectly achieve this effect? 有没有办法直接实现这一目标,或间接实现这一效果?

It is possible to come close to the idea you're looking to do. 有可能接近你想要的想法。 This is not a general "bottom" type for all types in an inheritance chain. 对于继承链中的所有类型,这不是一般的“底部”类型。 Instead, it's a bottom type specific to traits that use generics. 相反,它是特定于使用泛型的特征的底部类型。 You need to reuse Nothing in the type definition within the inheritance structure. 您需要在继承结构中的类型定义中重用Nothing Take a look at List[_] to see how they've defined Nil : 看一下List[_] ,看看他们如何定义Nil

case class ::[A](value: A, next: List[A]) extends List[A]
case object Nil extends List[Nothing]

Hence, Nil is a List[A] for all A because the type parameter of list is defined as List[+A] . 因此, Nil是所有AList[A] ,因为list的类型参数被定义为List[+A]

This doesn't work: 这不起作用:

class Foo
abstract final class Xyzzy extends Foo
class Bar extends Foo

scala> import reflect.runtime.universe._
import reflect.runtime.universe._

scala> typeOf[Xyzzy] <:< typeOf[Foo]
res0: Boolean = true

scala> typeOf[Xyzzy] <:< typeOf[Bar]
res1: Boolean = false

It appears that Nothing is handled specially by the compiler. 似乎Nothing是由编译器专门处理的。

I mean you could do this 我的意思是你可以做到这一点

trait Foo
abstract final class Xyzzy extends Foo
implicit def XyzzyIsBottom[A <: Foo]: Xyzzy <:< A = null

// Example usage
class X extends Foo
def xyzzyToX(x: Xyzzy): X = x

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM