2016-06-13 16 views
11

OCamlにはパラメトリック多形性があり、これにはいくつかの制限があります。 Haskellは型クラスを通して、ad hoc多型を提供しています。これは明らかに、いくつかの状況で非常に便利です。また、OCamlのモジュールとファンクタのシステムは、ad hoc多型を作成できることもよく知られています。たとえば、Simon Shine hereの最近の大きな回答をご覧ください。OCamlファンクタ、ハスケル型クラス、および複数導出

私の指摘は、ハスケルでは、がいくつかのタイプのクラスを派生するタイプを作成することが可能であるということです。。例えば:

data Person = Person { firstName :: String 
       , lastName :: String 
       , age :: Int 
       } deriving (Eq, Show, Read) 

これはいくつかの特徴を(タイプPersonの許容値は、等価テストをサポートする印刷可能で、与えられた例で読み取り可能に)を有するタイプを定義することは非常に便利です。

私の質問は次のとおりです。OCamlで同じことを簡単に行うことはできますか? によって簡単に私は、言語の基本的な構文と多くの工芸品を意味します。やや具体的な例を与えることを

は、我々は目的がShowableReadableの両方を実装モジュールによってパラメータファンクタFを書くことである2人のOCamlの署名

module type Showable = sig 
    type t 
    val to_string : t -> string 
end 

module type Readable = sig 
    type t 
    val from_string : string -> t 
end 

があるとします。

+2

これは私が今まで見た中で最もよく書かれた質問の1つでなければなりません!誰かが答えを見つけることを願っています! – Lhooq

答えて

10

確かに、それは実際にはかなり簡単です。モジュールの組み込みを使用してください。

module type S = sig 
    include Showable 
    include Readable with type t := t (* destructive substitution *) 
end 

module F (M : S) = struct 
    let fake_id x = M.from_string @@ M.to_string x 
end 

破壊的な置換は、マニュアルで説明されています。http://caml.inria.fr/pub/docs/manual-ocaml/extn.html#sec234
残りは通常のモジュールのものである(完全な説明のためのマニュアルを参照してください)

一部数子-重いライブラリかなり構造的なサブタイプのこの種に依存していますたくさん。たとえば、ocamlgraphの各ファンクタは、独自のモジュール型引数を定義します。ここにはKruskal moduleの例があります。ファンクタは、サブフォームがSig.G(ほとんどのグラフモジュールによって実装されています)を実装するタイプKruskal.Gのモジュールを期待しています。

+0

ありがとう、これは実際には非常に簡単です!ある意味では、Haskellの型クラスのシステムと、OCamlのモジュールとファンクタの型は同等であると言えますか? –

+2

これは同等ではありません。 [Modular Type Classes](http://www.cse.unsw.edu.au/~chak/papers/mtc-popl.pdf)で説明されているように、MLのモジュールシステムは、Haskellの型クラスよりも柔軟性が高く一般的ですが、再帰を許さない。それらを組み合わせると、ファンクタアプリケーションを手動で記述する必要はありませんが、Haskellのタイプごとにインポートされるタイプクラスインスタンスが1つしかないという問題も回避します。相違の概要については、Stefan Wehrの[ML Modules and Haskell Type Classes:建設的比較](http://www.stefanwehr.de/publications/Wehr_ML_modules_and_Haskell_type_classes.pdf)pp。107-110を参照してください。 –

+3

訂正:私よりもスマートな人が指摘しています。オレグ・キショフ(Oleg Kiselyov)は、この記事を見つけることはできませんが、Haskellタイプのクラスは、タイプレベルの関数を提供するMLモジュールよりも強力ですが、この記事を見つけることはできませんが、これ以上の大胆な記述は避けて、クールなコードスニペットを書くことに戻ります。 ;-) –

関連する問題