在Scala中匹配语句案例对象

时间:2017-10-01 17:55:45

标签: eclipse scala object match case

我目前正在Scala开展一个项目并遇到了一个小问题。

我目前正在使用匹配语句来确定案例对象的类型。我通过这样说:

abstract class Symbol
case object program extends Symbol
case object stmt_list extends Symbol
case object stmt extends Symbol
case object expr extends Symbol
case object term_tail extends Symbol
case object term extends Symbol
case object factor_tail extends Symbol
case object factor extends Symbol
case object add_op extends Symbol
case object mult_op extends Symbol


 def expected_symToIndex(expected_sym: Symbol): Int = expected_sym match {

    case program => 0
    case stmt_list => 1
    case stmt => 2
    case expr => 3
    case term_tail => 4
    case term => 5
    case factor_tail => 6
    case factor => 7
    case add_op => 8
    case mult_op => 9

  }

在Eclipse中,这给了我一个警告说

  

"变量模式后的模式无法匹配(SLS 8.1.1)如果您   打算与包中的对象程序匹配,你必须   使用反引号,例如:案例程序⇒"

在第一行。其他一切都是无法访问的代码。

测试我的程序后,此方法始终返回0(因为它始终在方法中的第一个案例对象行上执行)。我一直在寻找案例对象匹配方法,但是没有发现很多类似于此处所发生的内容。我很困惑,因为这些符号本身并不是变量;它们是我在匹配声明中检查的类型。

此外,围绕"计划"和反引号的其他测试值都不起作用。当我尝试这样的东西来测试类型时:

case a: program => 0

编译器告诉我类型"程序"无法找到。

谢谢!

2 个答案:

答案 0 :(得分:1)

您的programstmtexpr等被定义为object而不是class es,因此它们不是值而非类型。这可以解释为什么你不能使用case a: program =>

此外,Scala中的匹配/大小写与您描述它的方式不同。如果在x match { case a => ... }之类的情况下使用变量,那么程序不会检查x是否等于a然后继续运行... - 不会匹配任何值并将其分配给变量a,所以你可以使用...内部来引用匹配的值。

如您所述,这不是您想要做的。如果您不想匹配任何值并分配它,而是匹配变量的特定值,则可以使用反引号标记变量(正如错误消息试图告诉您的那样),如此x match { case `a` => ... }。 / p>

或者,您可以将object标记为case object,其中(除其他外)告诉编译器您打算使用它们进行匹配。

另见https://alvinalexander.com/scala/scala-unreachable-code-due-to-variable-pattern-message

答案 1 :(得分:1)

尝试定义case class而不是case object。然后,您应该能够在模式匹配中使用它们。

abstract class Symbol

case class program() extends Symbol

case class stmt_list() extends Symbol

case class stmt() extends Symbol

case class expr() extends Symbol

case class term_tail() extends Symbol

case class term() extends Symbol

case class factor_tail() extends Symbol

case class factor() extends Symbol

case class add_op() extends Symbol

case class mult_op() extends Symbol


object Main {

  def expected_symToIndex(expected_sym: Symbol): Int = expected_sym match {

    case x: program => 0
    case x: stmt_list => 1
    case x: stmt => 2
    case x: expr => 3
    case x: term_tail => 4
    case x: term => 5
    case x: factor_tail => 6
    case x: factor => 7
    case x: add_op => 8
    case x: mult_op => 9
    case _ => -1
  }

  def main(args: Array[String]): Unit = {

    println(expected_symToIndex(program())) //prints 0
    println(expected_symToIndex(stmt_list())) //prints 1

  }
}