79

在 Scala 中,如果我定义了apply在类或顶级对象中调用的方法,则只要我将一对括号附加到该类的实例并将适当的参数apply()放在它们之间,就会调用该方法。例如:

class Foo(x: Int) {
    def apply(y: Int) = {
        x*x + y*y
    }
}

val f = new Foo(3)
f(4)   // returns 25

所以基本上,object(args)只是object.apply(args).

Scala 如何进行这种转换?

这里是否有全局定义的隐式转换,类似于 Predef 对象中的隐式类型转换(但种类不同)?还是有更深层次的魔法?我之所以这么问,是因为 Scala 似乎强烈倾向于一致地应用一组较小的规则,而不是包含许多例外的许多规则。这最初对我来说似乎是一个例外。

4

3 回答 3

67

我认为没有比您最初所说的更深入的事情了:它只是语法糖,编译器将其转换f(a)f.apply(a)特殊的语法案例。

这似乎是一个特定的规则,但其中只有少数(例如, with update)允许类似DSL的构造和库。

于 2009-08-03T18:33:39.630 回答
20

实际上是相反的,带有apply方法的对象或类是正常情况,而函数是使用apply方法隐式构造同名对象的方法。实际上,您定义的每个函数都是 Function n特征的子对象(n 是参数的数量)。

有关该主题的更多信息,请参阅第6.6 节:Scala 语言规范的函数应用程序。

于 2009-08-03T18:28:27.580 回答
8

我之所以这么问,是因为 Scala 似乎强烈倾向于一致地应用一组较小的规则,而不是包含许多例外的许多规则。

是的。而这条规则属于这个较小的集合。

于 2009-08-03T21:07:40.287 回答