[英]An concrete simple example to demonstrate GADT in OCaml?
我在OCaml中搜索过GADT的概念,我们为什么需要它以及何时使用它等等。
我知道GADT不仅仅是在OCaml中,而是一个更通用的术语。
我发现了
http://caml.inria.fr/pub/docs/manual-ocaml-400/manual021.html#toc85
http://www.reddit.com/r/ocaml/comments/1jmjwf/explain_me_gadts_like_im_5_or_like_im_an/
等等,但其中一些是在Haskell中,而其他一些在没有GADT和GADT之间没有很好的比较例子。
所以我想要的是一个简单而又好的具体例子,我可以看到,如果没有GADT,事情就不好了。
我可以请那个吗?
GADT有两个原因。
第一个(也是最常见的一个)是关于动态类型:你可以添加一些动态类型,而不会丢失它的静态检查。 但这并不简单,但你可以确定你的类型条件将得到满足。 最简单的例子在ocaml手册中给出。 这在标准库中用于以类型安全的方式重写printf(在此之前,它是一个非常可怕的Obj.magic集合)
您可能想要使用GADT的第二个原因是,您希望在类型结构上保留一些复杂的不变量。 这很难表达,你经常需要付出很多努力才能做到这一点。 好吧,我没有任何方便的例子,但我曾经看到一位朋友写下AVL树的实现,如果打字系统证明平衡是正确的,这很酷。
对于更多的GADT功能及其良好的使用案例,您可以阅读Mads Hartmann撰写的相当不错的博客文章 。
我也在寻找GADT的良好应用,因为大多数时候,当我迟早使用它们时,我发现,没有它们也可以这样做,并且通常以更清洁的方式。 所以,这不是一个完整的调查,只是我自己的经验。
普遍价值观,又名存在感。 它们允许您创建异构容器和类型安全序列化。 请参阅Core的Univ
和Univ_map
模块示例。
语法树的类型安全评估程序。 这里GADT对于删除一些运行时检查很有用。
纯粹且类型安全的Printf
实现 ,已经是OCaml的一部分,也使用GADT重写
以下是如何使用GADT的真实例子 。 在该示例中,我使用GADT指定表关系,例如one_to_one
, one_to_many
等。根据使用的关系,相应地推断函数类型。 例如, one_to_maybe_one
关系返回一个函数'a -> 'b option
, one_to_many
创建一个带有'a -> 'b list
的函数。 只需创建几个不同的函数,例如link_one_to_one
, link_one_to_many
等,而不是一个函数link ~one_to:relation
,就可以实现同样的link ~one_to:relation
。 因此,人们可以认为这种方法是可论证的。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.