1

我有一个库,通用数据类型是在仅签名模块中定义的(将该签名复制到实现没有意义,因为它不包含任何功能):

(* b.mli *)
type bar = A of int | B of float

(* a.ml: *)
let foo = function B.A i -> B.A (i+1)
                 | B.B f -> B.B (f +. 1.)

(* c.mllib *)
A
B

在上面的设置中, ocamlbuild 无法创建库并出现一个相当令人惊讶的错误:

choeger@daishi /tmp/test % ocamlbuild c.cmxa
Solver failed:
  Ocamlbuild cannot find or build c.ml.  A file with such a name would usually be a source file.  I suspect you have given a wrong target name to Ocamlbuild.

我可以在 mllib 文件中不指定 B 的情况下进行构建,但随后类型栏变得抽象(这不是有意的)。有没有办法使用 ocamlbuild包含签名?

4

1 回答 1

2

您不能将B模块打包到库中,因为它不存在。你只有编译过的接口,没有编译过的模块,即编译单元。的目的cmxa是成为已编译代码的容器,因为您的B界面不包含任何代码,因此无法将任何内容放入库中。这意味着,您根本不需要将对模块 B 的引用放入mllib文件中。

一种更常见的方法是将类型和接口放入ml文件中而没有mli一个。我认为这种方法比mli唯一方法更好,因为它允许使用类型驱动的代码生成器,例如,使用mli唯一方法你不能执行以下操作:

type bar = A of int | B of float with sexp

但是,如果您仍然想拥有 a mliml那么我建议您使用oasis. 它有一个名为 的功能pure_interface,允许您构建此类库。

于 2015-01-08T15:00:14.397 回答