根据 OCaml 中的条件追加到列表



我正在尝试通过附加到列表来创建唯一列表,但是我收到此错误。

Error: This expression has type 'a list
       but an expression was expected of type unit

in_list 是一个布尔函数,用于检查值是否在列表中。

if(in_list x seen_list) then print_string("Already found") else seen_list@x in
    List.iter uniq check_list;;

似乎必须为追加函数修复一些小的语法错误。建议?

TL;DR:列表在 OCaml 中是不可变的

根据您的代码,您似乎认为列表在 OCaml 中是可变的,但事实并非如此。 因此seen_list@x计算一个新列表,但不会更改seen_list

您可以将代码更改为

let uniq seen_list x =
   if in_list x seen_list then
     (Printf.printf: "uniq: %d: Already seen.n" x; seen_list)
   else x :: seen_list
in
List.fold_left uniq [] check_list

uniq函数将整数列表映射到不重复的整数列表,并记录它跳过的条目。

我想,这段代码显然是用来学习的,但是你应该知道,它很可能实现了画家Shlemiel的算法。

这是一个类型错误,而不是语法错误。

OCaml 函数必须始终返回相同类型的结果。现在,当项目在列表中时,您的函数尝试返回与项目不在列表中不同的类型。

具体来说,当项目已经存在时,您的函数调用 print_string ,返回 () 。这称为unit,是一个不表示有趣值的占位符。当该项尚不存在时,函数将返回类型为 'a list 的值。几乎可以肯定的是,您需要做的是在所有情况下返回一个列表。

如果不看到更多代码,很难说更多,但处理这种情况的最常用方法是在项目已经存在时返回旧列表,当项目不存在时返回新的、更长的列表。

更新

此代码中有很多事情需要修复,但这就是我假设的练习的重点。

你的下一个问题似乎是List.iter是一个命令式函数,即它想要某事而不是产生结果。因此,它遍历列表的函数应该返回单位(如上所述)。您改用函数 uniq,它返回一个列表。

如果你想使用像 List.iter 这样的高阶函数,这是优秀的 OCaml 风格,你将需要使用折叠(List.fold_leftList.fold_right),其目的是累积结果。

相关内容

  • 没有找到相关文章

最新更新