需要澄清Scala文字标识符(反引号)

myt*_*mer 54 scala

在Scala阅读编程第二版和我发现了这个:

文字标识符"我们的想法是,您可以将运行时接受的任何字符串作为反引号之间的标识符"

我不完全确定为什么要使用它?本书给出了在Java的Thread类中访问静态yield方法的用例.

因此,在Scala中,yield是一个保留字,如果我使用带有反引号的yield,

Thread.`yield`()
Run Code Online (Sandbox Code Playgroud)

它会忽略Scala的产量并让我访问Java的Thread类的方法产量而不是?

先感谢您.

Deb*_*ski 109

究竟.使用反引号,您可以或多或少地为字段标识符指定任何名称.事实上,你甚至可以说

val ` ` = 0
Run Code Online (Sandbox Code Playgroud)

它定义了一个带有名称的变量(one character of whitespace).

The literal definition of identifiers is useful in two cases. The first case is, when there is already a reserved word of the same name in Scala and you need to use a Java library which does not care about that (and of course, why should it).

The other use case comes with case声明.惯例是小写名称引用匹配变量,而大写名称引用外部作用域的标识符.所以,

val A = "a"
val b = "b"
"a" match {
  case b => println("b")
  case A => println("A")
}
Run Code Online (Sandbox Code Playgroud)

打印"b"(如果编译器足够愚蠢,不会失败,说case A无法访问).如果要引用最初定义的val b,则需要使用反引号作为标记.

"a" match {
  case `b` => println("b")
  case A => println("A")
}
Run Code Online (Sandbox Code Playgroud)

哪个打印"A".

添加在最近的问题方法中有一个更高级的用例,带尖括号(<>),需要反引号才能让编译器消化setter方法的代码(它本身使用了一些'魔术'语法).

  • 文字标识符可能非常有用的另一种情况:使用Play的JSON API以Scala保留字作为字段名(例如`{“ type”:“ foo”}`)生成JSON。http://stackoverflow.com/a/34018822/56285 (2认同)

Mic*_*vin 16

谢谢@Debilski,它帮助我从AKKA doc了解下面的代码:

class WatchActor extends Actor {
    val child = context.actorOf(Props.empty, "child")
    ...
    def receive = {
        ...
        case Terminated(`child`) ? ...
    }
}
Run Code Online (Sandbox Code Playgroud)

案子 :

case Terminated(`child`)
Run Code Online (Sandbox Code Playgroud)

匹配Terminated类型的消息与ActorRef字段等于前面定义的子.

有了这个声明:

case Terminated(c)
Run Code Online (Sandbox Code Playgroud)

我们将每个Terminated消息与c中映射的ActorRef的任何引用相匹配.