我试图了解在Scala中使用curring优于部分应用程序的优势。请考虑以下代码:

  def sum(f: Int => Int) = (a: Int, b: Int) => f(a) + f(b)

  def sum2(f: Int => Int, a: Int, b: Int): Int = f(a) + f(b)

  def sum3(f: Int => Int)(a: Int, b: Int): Int = f(a) + f(b)

  val ho = sum({identity})
  val partial = sum2({ identity }, _, _)
  val currying = sum3({ identity })

  val a = currying(2, 2)
  val b = partial(2, 2)
  val c = ho(2, 2)

因此,如果我能这么容易地计算出部分应用函数,那么currying的优点是什么?

最佳答案

如果第二个参数部分是函数或按名称参数,则通常使用Currying。这有两个优点。首先,函数参数可以看起来像用括号括起来的代码块。例如。

using(new File(name)) { f =>
  ...
}

这比未处理的替代方法更好看:
using(new File(name), f => {
  ...
})

其次,更重要的是,类型推断通常可以找出函数的参数类型,因此不必在调用站点中给出。
例如,如果我在像这样的列表上定义max函数:
def max[T](xs: List[T])(compare: (T, T) => Boolean)

我可以这样称呼它:
max(List(1, -3, 43, 0)) ((x, y) => x < y)

甚至更短:
max(List(1, -3, 43, 0)) (_ < _)

如果我将max定义为非 curry 函数,则将无法正常工作,我必须像这样调用它:
max(List(1, -3, 43, 0), (x: Int, y: Int) => x < y)

如果最后一个参数不是函数或名称参数,我不建议使用currying。 Scala的_注释几乎是轻量级的,更灵活的且更清晰的IMO。

10-08 14:31