使用functor作为OCaml中的接口

Jac*_*ack 8 ocaml interface functor

我正在开发OCaml中的一些算法,这些算法需要一些部分是"可插拔的",因此部分计算留给特定的计算器.

举个例子假设我有一个像这样的签名:

module type Algorithm = sig
    val feed : float -> unit
    val nth : int -> (float -> float)
end
Run Code Online (Sandbox Code Playgroud)

而两种不同的实现,这将是Alg1Alg2.该Algorithm模块应该代表这两个实现的各种实现的接口.

现在我需要另一个组件,让我们称它为Executor将使用Alg1Alg2通过其接口的模块.

阅读仿函数似乎我需要一个仿函数来获取Algorithm并生成一个ConcreteExecutor具有我需要的算法的特定实现.所以这Executor是一种在其中一个组件上进行参数化的模块.

我对吗?这是获得我需要的最佳方式吗?我想这些想法是因为我来自Java/C++背景所以我习惯使用接口和抽象类,我需要以正确的方式进入这个functor/module抽象问题.

获取我想要的东西的正确语法是什么?

提前致谢

Nik*_*chi 4

是的,听起来函子就是你想要的。事实上,你可以看看标准库是如何使用函子的,因为源代码是可用的。在我的机器上,它位于 /usr/lib/ocaml/3.10.2/。例如,set.mli 包含以下内容:

module type OrderedType =
  sig
    type t
    val compare : t -> t -> int
  end

module type S
  sig
    ...
  end

module Make (Ord : OrderedType) : S with type elt = Ord.t
Run Code Online (Sandbox Code Playgroud)

当你想在 OCaml 中使用集合时,你可以:

module SSet = Set.Make(String);;
Run Code Online (Sandbox Code Playgroud)

因此,在您的代码中,Algorithm 替换了 OrderedType,Alg1/Alg2 替换了 String,Executor 替换了 Make,ConcreteExecutor 是 Executor(Alg1/Alg2) 的结果。您还会注意到 string.mli/ml 不包含任何有关 OrderedType 的提及。String 是一个 OrderedType,因为它具有由函数比较使用的类型 t。您不需要明确说明 String 是 OrderedType。