2009-03-12 11 views
12

functor(とその結果の型です)に少し問題があります。以下では、Ordered型を使用するSetファンクタがあります。私は実際にいくつかのガイダンスのためにocamlに付属のset.mlを使用しましたが、私はすべてをやっているようです。ahhem権利。私は整数でOrderedモジュールを作成し、このコードサンプルの最後のモジュールIntSetを取得するためにSetファンクタに適用しました。OcamlのFunctor

整数を挿入しようとすると、次の行が失敗します。

Error: This expression has type int but is here used with type 
     SetInt.elt = Set(OrdInt).elt 

私は間違っていない、タイプシステムはここに正しいです。トップレベルはSetInt.eltのタイプがSet(OrdInt).eltであると報告していますが、ocamlが提供するものを使用してSetを設定するために同じ操作を行うと、同じラインはSetInt.elt = OrderedInt.tとなります。私はSetInt.elt = Ordered.tを得ているようです。

これは簡単なことですが、私はおそらくちょっとしたばかげた部分を見逃しています!アー!

注:この問題はタイプと関係があるため、ここでメンバー/挿入関数を簡略化しました。

module type Ordered = 
    sig 
    type t 
    val lt : t -> t -> bool 
    val eq : t -> t -> bool 
    val leq : t -> t -> bool 
    end 

module type S = 
    sig 
    type elt 
    type t 
    exception Already_Exists 
    val empty : t 
    val insert : elt -> t -> t 
    val member : elt -> t -> bool 
    end 

module Set (Elt:Ordered) : S = 
    struct 
    type elt = Elt.t 
    type t = Leaf | Node of t * elt * t 
    exception Already_Exists 
    let empty = Leaf 
    let insert e t = t 
    let member e t = false 
    end 

module OrdInt : Ordered = 
    struct 
    type t = int 
    let lt a b = a < b 
    let eq a b = a = b 
    let leq a b = a <= b 
    end 

module IntSet = Set (OrdInt) 

(* line that fails *) 
let one_elm = IntSet.insert 1 IntSet.empty 

答えて

14

あなたはこれらがなければ

module Set (Elt:Ordered) : S with type elt = Elt.t = 
module OrdInt : Ordered with type t = int = 

に以下の2行

module Set (Elt:Ordered) : S = 
module OrdInt : Ordered = 

を変更する必要があり、モジュールはintとしてELTとtのタイプを公開署名を持っていません。

[編集]: set.mlには 'with'ビットがありません。これは、ファンクタの署名を宣言しているsml.mliがあり、 'with'を持っているためです。

module IntSet = Set (struct 
type t = int 
let lt a b = a < b 
let eq a b = a = b 
let leq a b = a <= b 
end) 

module OrdInt = 

あなたはまた、場所にモジュールを定義することによって設定構築することができます:あなたが明示的にこのように、それのために署名を指定しない場合にも、OrdIntは「で」必要はありません。