模式匹配`@`符号

Kev*_*ith 57 scala pattern-matching

鉴于此Person案例类:

scala> case class Person(name: String, age: Int) {}
defined class Person
Run Code Online (Sandbox Code Playgroud)

......而这个例子

scala> val b = Person("Kevin", 100)
b: Person = Person(Kevin,100)
Run Code Online (Sandbox Code Playgroud)

是否有理由喜欢这个代码(有@)

scala> b match {
     |    case p @ Person(_, age) => println("age")
     |    case _ => println("none")
     | }
age
Run Code Online (Sandbox Code Playgroud)

...以下?

scala> b match {
     |    case Person(_, age) => println("age")
     |    case _ => println("none")
     | }
age
Run Code Online (Sandbox Code Playgroud)

也许我错过了意义/力量@

whe*_*ies 94

您只需要包含@您想要处理对象本身的时间.因此:

that match{
  case p @ Person(_, age) if p != bill => age
  case Person(_, age) => age - 15
  case _ => println("Not a person")
}
Run Code Online (Sandbox Code Playgroud)

否则,包含它并没有真正的意义.

  • @Val我花了很多时间思考这个问题,直到最近才发现它.这是因为冒号(不是分号)匹配类型,但并非所有提取器都这样做.如果你创建一个自定义提取器,并且它嵌套在任何类型的另一个提取器中,你可能想要引用自定义提取器匹配的对象,但是自定义提取器可能不会是该对象类型的名称,所以冒号不合适. (3认同)
  • 您使用分号来引用对象本身.我想知道为什么分号不被重用`来引用对象本身`? (2认同)
  • @Val:他的代码中没有分号? (2认同)

Pra*_*n L 7

关于上述答案的评论.

考虑这个案例类.

case class Employee(name: String, id: Int, technology: String)
Run Code Online (Sandbox Code Playgroud)

在进行模式匹配时.

case e @ Employee(_, _, "scala") => e.name // matching for employees with only scala technology ... it works

case x: Employee => x.name // It also works

case e: Employee(_, _, "scala") => e.name // matching for employees with only scala technology ... **wont't work**
Run Code Online (Sandbox Code Playgroud)

  • 这种情况不需要`@`结构.你可以做`case Employee(name,_,"scala")=> name` (5认同)