OCaml中function关键字用法及reverse函数实现的技术疑问
OCaml中
function关键字的用法与列表反转函数的常见疑问 一、function关键字的本质
let f = function | ...是*fun x -> match x with | ...的语法糖*,它会自动为函数创建一个参数,并直接对这个参数做模式匹配。比如:
let f = function | [] -> 0 | _ -> 1
完全等价于:
let f = fun x -> match x with | [] -> 0 | _ -> 1
如果是多参数场景,比如你看到的aux acc = function ...,这其实是柯里化的写法,等价于:
let rec aux acc x = match x with | [] -> acc | hd :: tl -> aux (hd :: acc) tl
也就是aux是一个接受两个参数的函数,先传acc,再传待匹配的列表参数。
二、你的代码出错的原因
你写的错误版本里:
let rec aux acc = match aux with | [] -> acc | hd :: tl -> aux (hd :: acc) tl
这里的match aux with是在匹配函数aux本身,而不是匹配传入的第二个列表参数。aux是一个函数,类型是'a list -> 'a list -> 'a list,而你试图用列表的模式([]、hd::tl)去匹配函数,必然会触发类型不匹配错误。
正确的写法应该是明确对第二个参数做匹配,比如改成双参数+match:
let reverse lst = let rec aux acc lst = match lst with | [] -> acc | hd :: tl -> aux (hd :: acc) tl in aux [] lst
三、为什么aux看似单参数却能传两个参数?
这是OCaml的柯里化特性导致的。OCaml里所有多参数函数本质都是单参数函数的嵌套:
aux acc = function ...定义的aux,是一个接受acc后返回另一个函数的函数,返回的这个函数会接受列表参数并做模式匹配。- 所以调用
aux [] lst时,其实是先把[]传给aux,得到一个等待接收列表参数的函数,再把lst传给这个函数,最终完成调用。
换句话说,aux [] lst和(aux []) lst是完全等价的,这就是柯里化函数的调用方式。
内容的提问来源于stack exchange,提问作者EZVac
相关产品推荐
相关产品推荐

