【问题标题】:Ocaml: Equivalence of two listsOcaml:两个列表的等价性
【发布时间】:2018-04-07 20:03:59
【问题描述】:

刚接触 Ocaml,一直在解决一个我还没有看到答案的问题。 我正在研究一个函数,其中有 2 个列表的元组被检查是否相等。 示例:

# equivalence ([1;2],[1;2]);;
- : bool = true
# equivalence ([1;2],[2;1]);;
- : bool = true
# equivalence ([1;2],[1]);;
- : bool = false

我的代码:

let rec equivalent(a,b) = match a, b with
| [], [] -> true
| [], _
| _, [] -> false
| c::cc, d::dd -> if c = d then equivalent(cc,dd) else false;;

我知道问题出在最后一行。如果所有元素的顺序相同,我可以得到 true 的结果,但乱序是 false 的结果。我在浏览一个列表以查看另一个列表是否包含该元素时遇到了麻烦。我尝试使用 List.nth、.hd 和 .tl(不允许使用 .map 或 .itr)并且还尝试避免 Ocaml 的命令式特性。有什么建议或我应该看的地方吗?谢谢。

【问题讨论】:

  • 您的具体要求是什么?当两个列表具有不同的顺序(列表的一个重要属性)时,它们通常不被认为是等效的。你想把它们当作集合吗?你想把它们当作多重集吗?
  • 一般要求是不要使用任何命令式特性,如嵌套的 let 函数,使用 let 声明变量,以及 Ocaml 手册中列出的所有命令式特性。
  • 我对 Ocaml 中的集合没有真正的经验。需要列表,但我想我无法像对待一组想要对待的那样对待它们。基本上,不知道如何判断每个列表如何具有相同的值,而不是它们的顺序相同。不要求答案,但在某个地方寻找会有所帮助。
  • 要么测试一个列表的每个值是否包含在另一个列表中(和反向),要么对两个列表进行排序,然后测试它们的(列表)等价性。
  • 您说您正在尝试对列表进行排序。它看起来像这样:let sorted_list = List.sort compare unsorted_list in ... 如果您先对列表进行排序,那么检查是否相等会容易得多。 (事实上​​,你现有的代码看起来已经很接近了。)

标签: functional-programming ocaml


【解决方案1】:

我认为这是一些家庭作业,您必须将列表视为穷人。

正如 Bergi 提到的性能方面,最好的办法是先对两个列表进行排序,然后将它们与现有代码进行比较。但这可能不是您应该解决的问题。

假设列表被修改为不重复条目的集合,那么 a 和 b 的等价意味着 a 包含 b 的每个元素,b 包含 a 的每个元素。

首先编写一个函数contains: 'a -> 'a list -> bool,用于检查项目是否在列表中。接下来是一个函数contains_all: 'a list -> 'a list -> bool,它使用 contains 检查第一个列表中的每个项目是否都在第二个列表中。然后给你

let equivalence a b = (contains_all a b) && (contains_all b a)

如果您的列表可以包含重复项,请先对列表进行排序。其他任何事情都太不切实际了。

注意:containsList.mem 的形式存在,如果您被允许使用的话。

【讨论】:

    猜你喜欢
    • 2020-06-03
    • 1970-01-01
    • 2011-11-29
    • 2014-12-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-08-03
    • 1970-01-01
    相关资源
    最近更新 更多