2012-12-03 36 views
1

我正在学习Jason Hickey's Introduction to Objective Caml。只是有一个关于嵌套函数(柯里化)的问题。了解嵌套函数的逻辑的更好方法(柯里格)

有一个存在的问题How to understand the "Currying" in Haskell?,但我想我正在寻求一个稍微不同的问题的答案。


它说,我们可以写let sum = fun i j -> i + j;;let sum = fun i -> fun j -> i + j;;

我的问题很简单:

我可以理解这样的上述定义:let sum = fun i -> i + fun j -> j;;

我知道它不会通过编译器,但我只是试图将这种OCaml function definition映射到mathematics functions

在我上面的想象中,我们可以轻松地在数学中编写函数f(i) = i + g(j); and g(j) = j

我应该总是做这种逻辑映射以便于理解吗?

回答

3

你的想象力并不是真的正确:f(i) = i + g(j)没有太大的意义,j在这里没有定义。

要理解fun i j -> foo的正确方法是将其视为更简单的语法糖fun i -> fun j -> foo

所有下面的定义是完全等价的:

let sum i j = i + j 
let sum i = fun j -> i + j 
let sum = fun i -> (fun j -> i + j) 
let sum = fun i -> fun j -> i + j 
let sum = fun i j -> i + j 

let sum i = 
    let add_i = fun j -> i + j in 
    add_i 

数学上,这可以写成(ⅰ↦(j↦I + J)),作为 函数空间(ℕ→(ℕ→一个元件ℕ))。

1

OCaml函数可以直接映射到数学符号或从数学符号直接映射。但是,您需要认识到数学符号是不明确的。功能值f(i),特定值i和功能f本身之间没有明确的区别。当一个意思是功能f本身时,通常会写f(i)。 (“让我们考虑一个函数f(i)= i + 1 ...这个函数是......”)要在OCaml中编写正确的代码,您必须清楚地看到您是使用函数本身还是使用值的功能。

当你在数学符号说,“考虑功能f(i,j)=i+g(j) where g(j)=j,你写的函数值。在OCaml中,这被翻译成

let f i j = 
     let g j = j in 
     i + g j;; 

let f = 
    let g = fun j -> j 
    in 
    fun i j -> i + g j;; 

如果您正在尝试写let sum = fun i -> i + fun j -> j;;,那么在数学表示法中,您会说“考虑函数sum,使得sum(i) = i + g,其中g是由g(j)=j定义的函数。“这在数学上是不正确的:你不能添加整数值i功能g只能添加一个整数i和功能g对其他一些整数j的表达。” i+g“是undefined,严格来说,要么写i + g(i)i+g(j),而要写i+g,这在数学上是如此,在OCaml中也是这样的,