Recursion Ocaml:将列表排序为等价类
我最近开始学习ocaml,但在解决问题时遇到了困难 目标: 给定一个整数列表和一个函数,根据给定函数将整数排序为等价类,作为另一个列表中的列表。等效列表的顺序必须与原始列表中给出的顺序相同 更新:我决定尝试在没有库函数的情况下让它工作 这是到目前为止我的代码。它编译但不运行。任何语法方面的帮助都将不胜感激Recursion Ocaml:将列表排序为等价类,recursion,functional-programming,ocaml,equivalence-classes,Recursion,Functional Programming,Ocaml,Equivalence Classes,我最近开始学习ocaml,但在解决问题时遇到了困难 目标: 给定一个整数列表和一个函数,根据给定函数将整数排序为等价类,作为另一个列表中的列表。等效列表的顺序必须与原始列表中给出的顺序相同 更新:我决定尝试在没有库函数的情况下让它工作 这是到目前为止我的代码。它编译但不运行。任何语法方面的帮助都将不胜感激 let buckets f lst = let rec helpfunction f lst newlist = match lst with | [] ->
let buckets f lst =
let rec helpfunction f lst newlist =
match lst with
| [] ->newlist
| h::t -> match newlist with
| [] -> helpfunction f lst [h]@newlist
| [a]::_ -> if f h a
then helpfunction f t [a::h]@newlist
else helpfunction f t ([a]::[h]@mylist
重要提示:这是一个家庭作业问题,所以我不是在寻找为我粘贴的代码。我试着在我的家里用逻辑来解释它,并在整体思维过程和语法方面提供一些帮助。一旦我开始工作,我会努力使它更有效率好吧,让我们试着解决这个任务,而不是实际执行:) 大致来说,算法如下所示:
x
x
添加到此列表中[x]
),并将其添加到目标列表中list.exists
,可以在此处使用。测试的内容也或多或少很清楚:相同等价类列表中的每个成员在定义上都是等价的,因此我们可以只取头部,使用p
将其与x
进行比较
问题是如何将整数添加到另一个列表中的列表中。列表是不可变的,所以我们不能把它放在那里。。。但是我们可以将目标列表转换,或者将其折叠到另一个列表中。我敢打赌你得到了提示:列表。向左折叠是另一个难题
因此,总结所有这些,我们可以得出以下“更精确”的算法
从空目标列表开始res
从源列表l
使用List.exists
检查res
中是否有列表lst
,例如其头部h
p x h=true
如果是,使用List。向左折叠将当前res
转换为新的lst
替换为x::lst
,并按原样复制所有其他等效类列表
如果否,则引入一个新的等价类(将[x]
添加到res
)
对源列表中的下一个整数重复2-5,直到其为空
实际上(几乎)遵循此算法的实现相对简单。但是它不是很有效,因为存在
,折叠
将在同一个列表上迭代两次,执行完全相同的检查。通过一些调整,应该可以在一次运行中完成,但这个无效的运行应该足够好,作为起点…您尝试的是获取输入中的每个元素,然后将其插入列表结果列表的某个位置。让我提出一种不同的方法
您从一个“输入列表”和一个空的“构建结果列表”开始
如果输入为空,则结果已完成并返回
否则,将输入拆分为head和tail(模式匹配已经这样做了)。接下来,将输入列表划分为与head等效的项和与head不等效的项。以第二个列表作为新输入,以(第一个列表::结果)作为新结果递归。您还没有问过特定的问题。您是否正在寻找帮助来编译代码(我看到一些错误)?或者你想知道你提出的方法是否可行吗?一点A,一点B。对我来说,第一步是让我的代码正常工作,然后我将关注在类列表上循环两次的效率。最好是一次性完成现有的工作和折叠。检查类列表是否为空(为当前项创建新类)。否则,检查head类是否等同于当前项(添加它并返回新的_class::tail)。我的想法是先从“愚蠢的”和简单的解决方案开始,用简单的语言一步一步地解释,而不需要代码。但我同意你…谢谢你的回复。我的源列表只是一个基本列表,而不是列表列表。你认为最好立即开始将列表排序为一个列表列表,每个内部列表只包含一项吗?@KonstantinStrukov我想我现在掌握了逻辑。上面新代码中的语法正确吗?“我的源代码列表只是一个基本列表,而不是列表列表”@LostinRecursion当然正确int list list
将是目标列表的类型,而不是源列表的类型。抱歉,如果我不清楚-我也是OCaml新手,如果没有代码,我很难解释解决方案:)注意:您可以使用let helper results=function[]->results |(head::)作为输入->…
感谢您的回复。我正试图根据你的建议实施和做出改变。我有点被困在名单的一部分。你认为嵌套匹配语句是最好的方法吗?\n我想我现在已经掌握了逻辑,尽管我正在学习高阶函数的语法。我在上面加了我的新代码。通常我