module - 在 OCaml 中包含两个模块时处理类型名称冲突

标签 module include ocaml

谁能帮我完成 Jason Hickey 书中的练习 12.5?

基本上,问题是如何在实践中避免由于“包含”而导致的以下冲突问题?谢谢。

# module type XSig = sig 
type t 
val x : t 
end;; 
# module A : XSig = struct 
type t = int 
let x = 0 
end;; 
# module B : XSig = struct 
type t = int 
let x = 1 
end;; 
# module C = struct 
include A 
include B 
end;; 

最佳答案

我不知道问题的确切含义,但关于您的代码片段,有各种非常不同的方式来解释您要执行的操作。

您目前正在做的是将 AB 密封在两个抽象的、不兼容的签名下,然后尝试将它们混合在一个模块中,结果却产生了名称冲突。

也许您只是想避免名称冲突。当然,最简单的解决方案是不要对 A.tB.t 类型使用相同的名称。那么就可以“不包含B”:

module C = struct
  include A
  let x_b = B.x
end

更好的解决方案是使用 OCaml 3.12 破坏性替换签名,with type t := foo,从模块 B< 中屏蔽类型 t/:

module C = struct
  include A
  type u = B.t (* rename B.t into 'u' to avoid name conflict *)
  include (B : XSig with type t := u)  (* replaces 't' by 'u' *)
end

您可能还希望模块 AB 的类型兼容。在这种情况下,你不能用抽象类型来封装它们。

module type XSig = sig 
  type t 
  val x : t 
end

module A = struct 
  type t = int 
  let x = 0 
end

(* if you want to check that A can be sealed by XSig, do it here,
   outside the main declaration *)
let _ = (module A : XSig)

module B = struct 
  type t = int 
  let x = 1 
end

module C = struct 
  include (A : XSig with type t := int)
  include (B : XSig with type t := int)
end
(* module C : sig
     val x = int
   end *)

在此示例中,A.tB.t 两种类型都被破坏性替换 := 删除。如果你希望你的模块 C 有一个类型 t,你可以写:

module C = struct 
  type t = int
  include (A : XSig with type t := t)
  include (B : XSig with type t := t)
end

或者,使用非破坏性替换(更改类型定义而不是删除它):

module C = struct 
  include (A : XSig with type t = int)
  include (B : XSig with type t := t)
end

manual page for destructive substitution type type t := ...了解更多详情,和 the one on the classic with type t = ... construction进行比较。

关于module - 在 OCaml 中包含两个模块时处理类型名称冲突,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/11081501/

相关文章:

c++ #include(什么函数在什么里面)

c - #include "existing file"失败 : no such file (C)

c - C 中的 OCaml 类型构造函数 = <unknown constructor>

parallel-processing - OCaml 的并行化能力状况如何?

ocaml - 使用 ppx_deriving 打印抽象语法树

react-native - 应用程序未构建 - 而且我还没有开始编写代码

module - OCaml 中的嵌套签名示例?

python - __getattr__ 在模块上

go - 在 Go 中锁定第三方包的特定版本

c# - Visual Studio XML 外部注释文件不起作用