Scala的密封抽象与抽象类

Łuk*_*Lew 64 scala class abstract sealed

sealed abstractabstractScala类有什么区别?

sep*_*p2k 83

不同之处在于密封类的所有子类(无论是否抽象)必须与密封类位于同一文件中.

  • 不那么明显的东西(至少不适合我:-))密封类的"大孩子"也可以在其他文件中:给定密封的A类; B延伸A; C扩展B. B必须与A在同一个文件中,但C可以保留在相同或另一个中. (31认同)
  • @SandorMurakozi如果你想实现这个目的,你必须将B声明为密封类.密封只涉及直接继承. (6认同)

Dan*_*ral 76

正如所回答的,所有直接继承密封类(抽象或非抽象)的子类必须在同一个文件中.这样做的一个实际结果是编译器可以警告模式匹配是否不完整.例如:

sealed abstract class Tree
case class Node(left: Tree, right: Tree) extends Tree
case class Leaf[T](value: T) extends Tree
case object Empty extends Tree

def dps(t: Tree): Unit = t match {
  case Node(left, right) => dps(left); dps(right)
  case Leaf(x) => println("Leaf "+x)
  // case Empty => println("Empty") // Compiler warns here
}
Run Code Online (Sandbox Code Playgroud)

如果Treesealed,则编译器会发出警告,除非最后一行被取消注释.

  • @ sasha.sochka假设我编译它并将其放在一个jar文件中,没有`sealed`关键字.这一切都是在那时编译的,包括`match`语句.现在,另一个用户抓住这个jar并_extends`Tree`_.没有什么可以阻止他这样做,但是,那时,`match`语句不再完整.由于他没有编译它,只是从你的jar中使用它,编译器无法警告_him_.而且由于你在创建jar时不知道它,它无法警告你. (6认同)