小编lam*_*wer的帖子

如何使用 OCaml 的 [@tailcall] 注释来断言尾递归?

在 OCaml 中,[@tailcall]注释可以让您断言特定的函数调用是尾调用(因此希望您的整个函数是尾递归的)。问题是:我应该将注释准确放置在哪里?

明显、简单的例子:

let rec f = function
  | 0 -> 0
  | x -> (f [@tailcall]) (x - 1) (* works like a charm *)
Run Code Online (Sandbox Code Playgroud)

但我不知道如何在“不太明显”的地方做到这一点:

let rec f = function
  | 0 -> 0
  | x -> (|>) (x - 1) f (* uh? *)
Run Code Online (Sandbox Code Playgroud)

从汇编代码中我可以看到,后一个示例被编译器识别为尾递归。所以直到有人实现[@tailrec]:我到底应该在哪里放置[@tailcall]注释?(如果在第二个例子中可能的话)

ocaml tail-recursion

6
推荐指数
1
解决办法
2446
查看次数

OCaml 中的外部和内部接口和信息隐藏

当从多个模块创建一个库时,我找不到一种很好的方法来向库的用户(外部接口)隐藏正确的信息,同时能够在内部接口上访问我需要的一切。

更具体地说,我有两个模块(文件 a.ml[i] 和 b.ml[i])。在 A 中,我定义了一些类型 t,这是我不想向用户隐藏的内部结构(外部接口)。

module A : sig
  type t
end
module A = struct
  type t = float
end
Run Code Online (Sandbox Code Playgroud)

在模块B,然后我想用秘密类型A.t

module B : sig
  create_a : float -> A.t
end
module B = struct
  create_a x = x
end
Run Code Online (Sandbox Code Playgroud)

这当然不会编译,因为 B 的编译单元不知道A.t.

我知道但不喜欢的解决方案:

  1. 将功能create_a移至模块A
  2. 复制A.tto的定义B并用一些欺骗类型检查器external cheat : `a -> `b = "%identity"

有没有其他方法可以A.tB不将此信息泄漏到图书馆界面的情况下了解in的类型?

ocaml module

4
推荐指数
1
解决办法
528
查看次数

标签 统计

ocaml ×2

module ×1

tail-recursion ×1