5

每次我写一些形式的东西

let scorePopulation f population =
  Array.map (fun i -> f i) population

我最终问自己我是否会写得更好

let scorePopulation f =
  Array.map (fun i -> f i)

反而。与第二种形式相比,以第一种形式编写它有什么优势吗?

另外,您将如何调用第一种形式和第二种形式的函数定义?

4

6 回答 6

12

你可以走得更远:

let scorePopulation = Array.map

就优点/缺点而言,我认为主要关注点通常是可读性。有时,当所有参数都存在时,更容易理解函数的作用。其他时候,您不需要编造无关变量名称这一事实胜出。

于 2011-09-09T21:33:45.473 回答
10

其实,利弊是一样的:命名。

原因是菲尔·卡尔顿的一句老话:

计算机科学中只有两个难题。缓存失效和命名事物。

如果命名事物很难(即昂贵),那么名称不应该浪费在不相关的事物上。相反,如果某物有名字,那么它很重要。

无点样式允许您省略名称。

优点是它允许您省略不相关的名称。

缺点是它允许您省略相关名称。

于 2011-09-10T01:45:06.497 回答
7

我认为部分应用是函数式编程的一个好处。为什么不利用它呢?它导致更少的冗余。

要记住的另一件事是值限制[MSDN]。没有参数的部分应用函数是函数。真函数可以泛化,但值不能。

于 2011-09-09T21:35:14.020 回答
6

您应该能够在第一个和第二个示例中以相同的方式调用它。这种技术通常称为无点样式。

可能会更好。它更短,所以默认情况下这是一个加号。我同意上面链接中的这个警告:

随着高阶函数被链接在一起,在心理上推断表达式的类型会变得更加困难。对表达式类型(显式函数参数和参数数量)的心理暗示消失了。

你也失去了给参数一个有意义的名字的机会,这有时可能有助于理解。

于 2011-09-09T21:34:15.747 回答
5

我个人讨厌无点风格,我总是觉得它不可读。正如其他人提到的,

你也失去了给参数一个有意义的名字的机会,这有时可能有助于理解。

总体而言,如果我在左侧定义一个命名函数,我通常希望看到列出的所有“预期”参数。(相比之下,部分应用程序非常适合匿名呼叫站点和本地 lambda,但我更喜欢在编写顶级代码时更明确/文档 - 范围越大,“软件工程”问题就越多。)

正如其他人所提到的,如果您从泛型函数中删除所有参数,“值限制”就会生效,这是一个技术限制,也略微阻碍了 F# 中的无点样式。

于 2011-09-09T21:51:01.553 回答
2

我经常提供参数,即使为了清楚起见我可以省略它。当我省略参数时,通常是因为函数体立即表明:i)有一个省略的参数,ii)参数的性质是什么。例如,我觉得写

let f = function [] -> "empty" | x::_ -> "not empty"

代替

let f l = match l with [] -> "empty" | x::_ -> "not empty"

一个更有趣的例子是写

let f = List.map g |> List.fold_left h

代替

let f l = List.map g (List.fold_left h l)

我觉得第一个更清楚。这里的好处来自于直观的高阶运算符的可用性,例如|>电池中提供的 。

于 2011-09-10T00:54:16.427 回答