在Scala 2.10.0中是否可以利用模式匹配中的case类继承?

时间:2013-06-19 09:30:54

标签: scala

我找不到这个简单问题的答案,也许我使用错误的关键字进行搜索。

要创建AST,我需要节点,如Number,Add,Sub,Mul,Div等。 由于许多数学运算共享相同的结构,我如何在相同的模式匹配情况下处理它们?例如。据说下面的行在句法上不正确:

object AST {
  sealed abstract class Expr
  case class MathOp(e1: Expr, e2: Expr) extends Expr
  case class Number extends Expr

  case class Add(e1: Expr, e2: Expr) extends MathOp(e1, e2)
  case class Sub(e1: Expr, e2: Expr) extends MathOp(e1, e2)
}

目的是能够做到:

expr match {
  case MathOp(e1: Expr, e2: Expr) => //do something that would be done to Add, Sub, Mul, Div
  case Number => //do another thing
}

2 个答案:

答案 0 :(得分:5)

案例类比添加模式匹配提取器所做的更多,例如它们增加了相等性,产品迭代器和arity等,因此odd things在继承下发生。因此,之前不推荐使用case类继承,现在Scala 2.10中不可能使用它。

对于您的情况,您需要自定义提取器(unapply方法):

object AST {
  sealed trait Expr
  object MathOp {
    def unapply(m: MathOp): Option[(Expr, Expr)] = Some(m.e1 -> m.e2)
  }
  sealed trait MathOp extends Expr {
    def e1: Expr
    def e2: Expr
  }
  case class Number extends Expr

  case class Add(e1: Expr, e2: Expr) extends MathOp
  case class Sub(e1: Expr, e2: Expr) extends MathOp
}

Related question

答案 1 :(得分:0)

据我所知,我没有理由为孩子们使用“案例类”。希望正确的代码如下:

object AST {
  sealed abstract class Expr
  case class MathOp(e1: Expr, e2: Expr) extends Expr
  case class Number extends Expr

  class Add(e1: Expr, e2: Expr) extends MathOp(e1, e2)
  class Sub(e1: Expr, e2: Expr) extends MathOp(e1, e2)
}

expr match {
  case MathOp(e1: Expr, e2: Expr) => //do something that would be done to Add, Sub, Mul, Div
  case Number => //do another thing
}