简体   繁体   English

Scala奇怪的方法调用语法

[英]Scala strange method invocation syntax

I was looking through the Specs2 quickstart guide and quickly came across some syntax I'm not familiar with: 我正在浏览Specs2快速入门指南,并迅速发现一些我不熟悉的语法:

"The 'Hello world' string" should {
 // more stuff here
}

Digging into the specs2 source, I see that should is a method of the class Described(s: String) . 深入查看specs2源,我看到shouldDescribed(s: String)类的方法。 Futhermore, Described appears to be instantiated somehow (as a method described ?) implicitly right before the class definition: 此外, Described似乎是在类定义之前隐式实例化的(作为described的方法?):

implicit def described(s: String): Described = new Described(s)
class Described(s: String) {
  def should(fs: =>Fragment) = addFragments(s, fs, "should")
}

I don't understand: 我不明白:

  1. What this implicit instantiation is all about 这个隐式实例化是关于什么的
  2. What in the world is going one with this syntax: "some string" should { ... } . 世界上正在使用这种语法: "some string" should { ... } Eg a string followed by a method call (naively this only makes sense to me if should were a method on the String class. 例如,一个字符串,然后一个方法调用(天真这只是对我来说很有意义,如果should是String类的方法。

I actually just came across this pattern which appears to answer my question: the Pimp my Library pattern that makes use of this implicit conversion pattern which I was unfamiliar with. 我实际上碰到了这种模式,似乎可以回答我的问题: Pimp my Library模式使用了我不熟悉的这种隐式转换模式。 Leaving open just in case its missing any important insight, and because the article was written by Odersky almost 10 years ago. 开放以防万一缺少任何重要见解,并且因为该文章是Odersky在大约十年前撰写的。

Looks like you've answered your own question, but I will post more details. 看来您已经回答了自己的问题,但我会发布更多详细信息。

The "Pimp my Library" name has been replaced with "Enriched Library" (for reasons that probably don't need an explanation, although I confess I chuckled when I first learned of pimping out libraries..) “ Pimp my Library”的名称已替换为“ Enriched Library”(出于某种原因,可能不需要解释,尽管我承认,当我初次了解如何配置图书馆时,我笑了起来。)

Implicits in Scala do 3 things: Scala中的隐式做3件事:

  • Allow implicit conversion from one type to another 允许从一种类型隐式转换为另一种类型
  • (by virtue of the above) allow you to safely extend existing classes in a non-global way. (基于以上所述)允许您以非全局方式安全地扩展现有类。
  • Allow passing of values by type, rather than by name. 允许按类型而不是按名称传递值。

The implicit extension methods pattern has been more formalized in Scala 2.10; 隐式扩展方法模式已在Scala 2.10中更正式化。 the above Described example in your question can be more succinctly written as an implicit value class: 您问题中的上述示例可以更简洁地编写为隐式值类:

implicit class Described(s: String) {
  def should(fs: =>Fragment) = addFragments(s, fs, "should")
}

I understand the compiler will emit more efficient code for implicit value classes, also, as it can skip the allocation of the wrapper class containing the extension methods. 我知道编译器还将为隐式值类发出更有效的代码,因为它可以跳过包含扩展方法的包装器类的分配。 See http://www.blog.project13.pl/index.php/coding/1769/scala-2-10-and-why-you-will-love-implicit-value-classes/ 参见http://www.blog.project13.pl/index.php/coding/1769/scala-2-10-and-why-you-will-love-implicit-value-classes/

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM