Ocaml错误列出了高阶函数

时间:2018-06-25 15:39:00

标签: ocaml

我试图编写一个高阶函数选择,该函数选择将f输出为true的元素,然后在列表中输出其值。

例如:

#let f a = if a>8 then true else false;;
pick [1;3;4;9;12;22] f;;
- : int list = [9;12;22]

到目前为止,我已经编写了这段代码,但是它不起作用:

let rec pick f list =
    let p1 = f list in
        if (List.hd(p1)==true)
            then List.hd(p1)::pick List.tl(p1)
        else pick  List.tl(p1)

错误:此表达式的类型为'a list        但是期望使用'b-> bool#

类型的表达式

我该如何更正它以便在列表上使用?

3 个答案:

答案 0 :(得分:3)

这是您的代码中的一些问题。

  • 您正在定义pick f list,但将其称为pick [list] f。确保您的参数顺序一致。 =>这是导致您收到错误消息的那一个。
  • 正如Nate C-K所说。您不能在整个列表上调用f,而只能在列表的元素上调用。
  • 除非已对列表进行了空性测试,否则请不要使用List.hdList.tl
  • 请勿将==用于结构相等,也不要将布尔值与相等使用。
  • if a>8 then true else false仅应替换为a>8

答案 1 :(得分:1)

使用表达式f list,您将列表list传递给函数f,这不是您想执行的操作。您只想在列表的开头调用f

通常,在这种情况下,OCaml程序员将使用模式匹配来解构列表,如下所示(我尚未测试此代码):

let rec pick f list =
  match list with
  | [] -> []
  | h::t -> if f h then h :: pick f t
                   else pick f t

答案 2 :(得分:0)

列表模块已经包含解决方案,它是功能过滤器

let f a = a > 8;;
List.filter f [1;3;4;9;12;22];;
- : int list = [9;12;22]

该函数在列表上进行迭代,将用于验证给定谓词的元素存储在累加器中并返回。

标准库包含许多标准方法,例如过滤器,建议您首先查看文档,因为这些功能可以解决大多数问题。

Inria的列表模块文档:

https://caml.inria.fr/pub/docs/manual-ocaml/libref/List.html