int - >之间有什么区别? int - > int和(int * int) - >在SML中的int?

时间:2016-10-14 01:15:52

标签: functional-programming sml smlnj ml

我注意到在SML中有两种定义函数的方法。例如,如果你使用add函数,这有两种方式:

import actions from './actions'

const reducer = (state = {}, action) => {
   if (actions[action.type]) return Object.assign({},
       state, actions[action.type](action)
   );
   return state;
}

第一种方法将函数类型创建为:

fun add x y = x+y;

fun add(x,y) = x+y;

第二个创建函数类型:

val add = fn : int -> int -> int

同一功能的这两种类型有什么区别?还有为什么同一个函数有两种类型?

2 个答案:

答案 0 :(得分:5)

如果我们从你的两个定义中删除语法糖,它们就变成了:

val add = fn x => fn y => x+y

val add = fn xy =>
    case xy of
        (x,y) => x+y

因此,在第一种情况下,add是一个接受参数x并返回另一个函数的函数,该函数接受参数y然后返回x+y。这种通过返回另一个函数来模拟多个参数的技术称为currying。

在第二种情况下,add是一个函数,它将一个元组作为参数,然后添加元组的两个元素。

这也解释了两种不同的类型。 ->是功能箭头,它与右侧相关联,这意味着int -> int -> int与描述采用int -> (int -> int)并返回int的函数的int -> int相同功能

另一方面,

*是用于元组类型的语法,即int * int是包含两个整数的元组类型,因此int * int -> int(括号为{{1}因为(int * int) -> int的优先级高于*,所以它描述了一个带有两个整数元组并返回一个int的函数。

答案 1 :(得分:0)

这两个函数不同的原因是Currying的现象。具体来说,Currying是使用dom(f) = R^{n}编写任何函数的功能,该函数从R n - 次获取输入。这基本上是通过确保每个输入返回下一个要接受的变量的函数来实现的。这就是->符号所代表的含义 - 它是Curry-Howard Isomorphism的基本结果。所以:

fun addCurry x y = x + y (* int -> int -> int *)
fun addProd (x,y) = x + y (* (int*int) -> int *)

告诉我们addCurry是将addProd缩减为可用于替代"的形式。并返回变量。因此,addProdaddCurry在上下文中是等效的。但是,它们在语义上等效。 (int*int)是产品类型。它表示它预计会input1=intinput2=intint -> int表示需要int并返回int。它是箭头型。

如果您有兴趣,您可能还想知道SML函数只有两种参数:

1)咖喱

2)元组 - 因此,fun addProd (x,y)表示(x,y)作为函数参数的元组。