Scala unapply方法

时间:2016-12-26 17:12:36

标签: scala pattern-matching unapply

我正在尝试了解scala unapply方法。

以下是我的理解。假设我有一个Person对象:

class Person(val fname: String, val lname: String)

object Person{
  def unapply(x: Person) : Option[(String, String)] = 
    Some(x.fname,x.lname)
}

new Person("Magic", "Mike") match {
  case Person(x, y) => s"Last Name is ${y}"
  case _ => "Unknown"
}

我认为这个案例叫做:

val temp = Person.unapply(new Person("Magic", "Mike"))
if (temp != None)  { val (x, y) = temp.get }
else { <go to next case> }

但是,如果我有以下情况,下面如何解除工作:

new Person("Magic", "Mike") match {
  case Person("Harold", y) => s"Last Name is ${y}"
  case Person("Magic", y) => s"Last Name is ${y}"
  case _ => "Unknown"
}

如何在unapply方法中访问fname(“Magic”)的值并给出与第一个相同/正确的结果?

1 个答案:

答案 0 :(得分:4)

使用scalac运行-Xprint:patmat将显示模式匹配阶段后句法树的外观:

scalac -Xprint:patmat test.scala

  case <synthetic> val x1: Person = new Person("Magic", "Mike");
  case10(){
    <synthetic> val o12: Option[(String, String)] = Person.unapply(x1);
    if (o12.isEmpty.unary_!)
      {
        <synthetic> val p3: String = o12.get._1;
        val y: String = o12.get._2;
        if ("Harold".==(p3))
          matchEnd9(scala.StringContext.apply("Last Name is ", "").s(y))
        else
          case11()
      }
    else
      case11()
  };
  case11(){
    <synthetic> val o14: Option[(String, String)] = Person.unapply(x1);
    if (o14.isEmpty.unary_!)
      {
        <synthetic> val p5: String = o14.get._1;
        val y: String = o14.get._2;
        if ("Magic".==(p5))
          matchEnd9(scala.StringContext.apply("Last Name is ", "").s(y))
        else
          case13()
      }
    else
      case13()
  };
  case13(){
    matchEnd9("Unknown")
  };

正如您所看到的,对于每个案例,它首先在匹配的对象上调用unapply,然后如果Option不为空(因此它已匹配),它会检查元组的元素之一等于期望值,如果是,则它匹配此情况的闭包。