【问题标题】:What exactly does this Standard ML code do?这个标准 ML 代码究竟做了什么?
【发布时间】:2010-12-16 01:46:44
【问题描述】:

我正在阅读 Chris Okasaki 的纯函数式数据结构,我遇到了一个问题。它位于here。特别是,我不明白rotateexec 函数是如何工作的:

fun rotate($Nil, y::_, a) = $Cons (y, a)
    | rotate ($Cons (x, xs), y :: ys, a) = 
        $Cons(x, rotate (xs, ys, $Cons (y, a)))

fun exec (f, r, $Cons (X, s)) = (f, r, s)
    | exec (f, r, $Nil) = let val f' = rotate (f, r, $Nil) in (f', [], f') end

有人可以用愚蠢的人的话来形容吗?我仍在学习基于 ML 的语言。 :-)

【问题讨论】:

  • 参见该书的第 4.1 节,了解$ 符号的解释;冈崎解释说,这是他的懒惰暂停符号。

标签: ml persistent-data


【解决方案1】:

这看起来不像我学习的标准 ML(在数据构造函数前面有 $ 字符),但也许事情已经改变了。总之:

首先第 2 行 rotate 有一个小错字,你在 $Cons 后面加了一个逗号

rotate 基本上采用三个列表的元组并按顺序组装它们:第一个 ++(第二个的反转)++ 第三个。但它通过同时从列表 1 和列表 2 中提取元素来线性地做到这一点。列表 1 的头部是最终结果(o(1) 操作)。但是列表 2 的尾部作为参数传递给递归调用,并且它的头部被 cons'd 到第三个参数上,这相当于反转它。

第三个参数基本上是一个累加器。在使用累加器作为参数的函数式编程中,这样可以避免更昂贵的计算。

我承认不理解 exec 的目的。上下文是什么?

【讨论】:

  • 美元符号是他的惰性求值符号。本质上,这是一个实时持久队列,您可以在其中将项目从尾部旋转到前面。
【解决方案2】:

这并不能解释整个事情,但请注意,在fun rotate($Nil, y::_, a) 中,y::_ 是一个匹配列表的模式,其中您将列表的头部(第一个元素)标记为 y 和尾部列表(第一个元素之后的每个项目)为__ 充当通配符模式。

查看SML on Wikipedia,特别是Mergesort 实现,了解更多:: 模式和_ 的使用。

【讨论】:

    猜你喜欢
    • 2017-06-11
    • 2021-08-22
    • 1970-01-01
    • 2012-07-23
    • 2016-09-10
    • 2023-03-15
    • 2012-10-17
    • 2021-06-04
    • 1970-01-01
    相关资源
    最近更新 更多