我的问题是,标准ML的模块系统和OCaml模块系统之间是否有任何区别? OCaml是否具有仿函数的所有支持...... SML有哪些?
答案 0 :(得分:51)
在功能方面以及语义方面存在一些差异。
功能SML支持但不支持OCaml:
let
功能OCaml 4有但不是SML:
sig with module A = M
)module type of
但是,有几个SML实现提供了一些扩展,例如:高阶仿函数(SML / NJ,莫斯科ML,Alice ML),本地和一等模块(莫斯科ML,Alice ML),模块共享(SML / NJ,Alice ML),嵌套签名(莫斯科ML,Alice ML)和递归模块(莫斯科ML)。
语义学上,最大的区别在于类型等价的处理,特别是关于仿函数:
在SML中,仿函数是生成,这意味着将相同的仿函数两次应用于同一参数总会产生新的类型。
在OCaml中,仿函数是 applicative ,这意味着将相同的仿函数两次应用于完全相同的参数(加上额外的语法限制)会再现等效类型。这种语义更灵活,但也可以打破抽象(参见我们在this paper中给出的例子,第8节)。
编辑:OCaml 4增加了生成仿函数的功能。
OCaml有一个纯粹的语法概念,这意味着类型系统无法表达某些类型的等价,并且会被静默删除。
编辑:请考虑以下示例:
module F (X : sig type t end) = struct type u = X.t -> unit type v = X.t end module M = F (struct type t = int end : sig type t end)
M
的类型只是sig type u type v end
,因此丢失了有关其类型u
和v
之间关系的任何信息,因为通常无法在表面语法。
另一个显着的区别是OCaml的模块类型系统是undecidable(即,类型检查可能不会终止),因为它允许抽象签名,SML不允许。
答案 1 :(得分:2)
至于语义学,Andreas Rossberg在上面给出了一个更好更精细的答案。但是,关于语法this site可能正是您要找的。 p>
答案 2 :(得分:0)
SML中也有abstype工具,它类似于数据类型工具,只是它隐藏了数据类型的结构。 OCaml依靠模块抽象来进行所有必要的隐藏。请注意,this site在SML中未提及此功能。