PP Laru
PP Laru

Reputation: 121

Signature mismatch when trying to use a module in another module

I'm having a problem where I have one module trying to use another one, but I'm getting an error claiming there's a signature mismatch and I'm not certain why. I was pretty sure I was doing this right though. Here's some code:

module type ITEM =
sig
    type item
    val leq : item * item -> bool
    val initial : item
end
module type HEAP =
sig
  type item
  type tree
  exception InitHeap
  val depth : tree -> int
  val initHeap : int -> tree
  val insert : item * tree -> tree
  val isHeap : tree -> bool
  val maxHeap : tree -> item
  val replace : item * tree -> item * tree
  val size : tree -> int
  val top : tree -> item
end

module Heap (Item: ITEM) : HEAP =
struct 
              type item = Item.item

    let leq(p, q) : bool = Item.leq(p,q)

    let max(p,q) = if leq(p,q) then q else p
    and min(p,q) = if leq(p,q) then p else q

    let intmax((p : int),q) = if p <= q then q else p

    type tree =
      | L of item
      | N of item * tree * tree

   exception InitHeap

   let rec initHeap n =
       if (n < 1) then raise InitHeap
       else if n = 1 then L Item.initial
            else let t = initHeap(n - 1)
                 in N (Item.initial, t, t)

    let rec top t =
      match t with
      | (L i) -> i
      | N (i,_,_) -> i


    let rec isHeap t =
      match t with
      | (L _) -> true
      | (N(i,l,r)) ->
        leq(i,top l) && leq(i,top r) && isHeap l && isHeap r

    let rec depth t =
      match t with
      | (L _) -> 1
      | N(i,l,r) -> 1 + intmax(depth l,depth r)

   let rec replace (i,h) = (top h, insert(i,h))
   and insert (i, h) =
     match h with
     | L _ -> L i
     | N (_,l,r) ->
       if leq(i,min(top l,top r))
       then N(i,l,r)
       else if leq((top l),(top r))
            then N(top l,insert(i,l),r)
            else N(top r,l,insert(i,r))

   let rec size h =
     match h with
     | L _ -> 1
     | N (_,l,r) -> 1 + size l + size r

   let rec maxHeap h =
     match h with
     | (L i) -> i
     | N (_,l,r) -> max(maxHeap l, maxHeap r)
end 

So Heap includes a bunch of functions that just do simple operations on a Heap but for some reason ocaml thinks that the signature for HEAP is supposed to include functions for ITEM, but I just want to pull ITEM functions into HEAP The error I get:

Error: Signature mismatch:
   Modules do not match:
     sig val leq : int * int -> bool end
   is not included in
     ITEM
   The value `initial' is required but not provided
   File "lab13.ml", line 28, characters 8-26: Expected declaration
   The type `item' is required but not provided
   File "lab13.ml", line 26, characters 8-17: Expected declaration

Thanks for any help in advance!

Upvotes: 0

Views: 851

Answers (1)

octachron
octachron

Reputation: 18892

You most probably wrote

module type HEAD = functor (Head:ITEM) -> sig … end  

(and not module type HEAD = functor (Head:HEAD) -> sig … end which is recursely using the HEAD module type which is a type error )

when you meant

module type HEAD = sig … end  

Adding the functor(HEAD:ITEM) -> … part makes HEAD the signature or a functor. Therefore

module Heap (Item: ITEM) : HEAP

is the same thing as

module Heap (Item: ITEM) : functor(Heap:HEAP) -> sig … end

in other words, the signature that you added make Heap a higher-order functor; which is obviously not the case of the implementation. Unfortunately, error messages in presence of functors are lacking right now, and the type-checker does not detail error in this specific case for now.

Rewriting the HEAD module type as

module type HEAD = sig … end

should fix this problem.

Upvotes: 1

Related Questions