Re: Typage des modules

From: Sylvain BOULM'E (Sylvain.Boulme@lip6.fr)
Date: Wed Jun 23 1999 - 15:19:06 MET DST


Message-Id: <199906231319.PAA13795@ventoux.lip6.fr>
To: Daniel Bonniot <dbonniot@ens-lyon.fr>
Subject: Re: Typage des modules
In-Reply-To: Your message of "Tue, 22 Jun 1999 17:38:54 +0200."
             <376FAE0E.9C1AD8AE@ens-lyon.fr>
Date: Wed, 23 Jun 1999 15:19:06 +0200
From: "Sylvain BOULM'E" <Sylvain.Boulme@lip6.fr>

Bonjour,

Pour repondre a votre question, il y a plusieurs solutions... La "meilleure"
depend du probleme que vous avez a resoudre :

1. Le polymorphisme de OCAML
 
Dans "b.mli", vous declarez
val f: 'a -> 'a

Si f utilise en fait des fonctions de "a.ml", vous passez ces fonctions en
parametres de f. Cette methode devient vite penible si vous avez en fait
plusieurs fonctions "f" qui dependent de plusieurs fonctions de "a.ml"

2. Dans ce cas, vous pouvez utilisez le mecanisme de foncteur de OCAML.
Par exemple :

module type B_Type =
  sig
    type t
    val f: t->t
  end

module MakeB (A: sig type a val g: a->a end) : B_Type with type t=A.a =
  struct
    type t=A.a
    let f x = (A.g x)
  end

module type A_Type =
  sig
    type a
    module B : B_Type with type t=a
    val v: a
    val g: a -> a
  end

module A: A_Type =
  struct
    type b = { x:int}
    type a = b
    let g x = x
    module B = MakeB (struct type a = b let g=g end)
    let v = B.f {x=3}
  end

module B = MakeB (A)

Dans cet exemple vous pouvez evidemment faire de "A_Type" un "a.mli", et de
"A" un "a.ml". Mais ce mecanisme devient penible quand les dependences se
compliquent (avec eventuellement des definitions de B et de A mutuellement
recursives) : dans ce cas, soit on peut revoir son decoupage en "module" (deux
fonctions mutuellement recursives devraient peut-etre appartenir au meme
module), soit on peut utiliser les mecanismes objets.

3.

class virtual ['a] a_type =
  object
    method virtual stop: 'a -> bool
    method virtual v: 'a
    method virtual g: 'a -> 'a
  end

class ['b] b_class (o:'b) =
  object
    constraint 'b = 'a #a_type
    method f x=
        if (o#stop x)
        then o#v
        else (o#g x)
  end

module type A_Type =
sig
  type a
  val obj : a a_type
  val p: a -> string
end

module A: A_Type =
struct
  type a={x : int}
  class a_class =
    object (s)
      inherit [a] a_type
      method b = new b_class s
      method stop y = y.x <= 0
      method v = s#b#f {x=3}
      method g y =
         if (s#stop y) then (s#b#f y) else { x= y.x-5 }
    end
   let obj = (new a_class :> a a_type)
   let p y = string_of_int y.x
end;;
    
let obj_b = new b_class A.obj;;

J'espere que vous trouverez ce que vous cherchez,

Sylvain.
                      



This archive was generated by hypermail 2b29 : Sun Jan 02 2000 - 11:58:23 MET