Loading ...
Sorry, an error occurred while loading the content.
 

constructed types question

Expand Messages
  • Julien Cohen
    Hello, I m trying to manage with constructed types in a particular way, can anyone tell me if it is a really bad way? I want to use a lists with an
    Message 1 of 3 , Oct 18, 2002
      Hello, I'm trying to manage with constructed types in a particular way,
      can anyone tell me if it is a "really bad" way?


      I want to use 'a lists with an additionnal type information : 'b.
      Here is the type declaration: (ocaml 3.04)

      # type ('a,'b) t = 'a list;;
      type ('a, 'b) t = 'a list

      I have a cons:

      # let f (x:'a) (y:('a,'b) t) = (x::y : ('a,'b) t);;
      val f : 'a -> ('a, 'b) t -> ('a, 'b) t = <fun>

      Then a value :

      # let (v: (int,bool) t) = [1];;
      val v : (int, bool) t = [1]


      The problem is when I do a "cons" on it:

      # f 1 v;;
      - : (int, '_a) t = [1; 1]

      the "bool" information has diseappeared !!

      Any ideas?

      Julien Cohen
    • Daniel de Rauglaudre
      Hi, ... This is strange, indeed. It deserves a message in the Caml List or at Caml bugs. -- Daniel de RAUGLAUDRE daniel.de_rauglaudre@inria.fr
      Message 2 of 3 , Oct 18, 2002
        Hi,

        On Fri, Oct 18, 2002 at 01:49:30PM +0200, Julien Cohen wrote:
        >
        > # type ('a,'b) t = 'a list;;
        > # let f (x:'a) (y:('a,'b) t) = (x::y : ('a,'b) t);;
        > # let (v: (int,bool) t) = [1];;
        > # f 1 v;;
        > - : (int, '_a) t = [1; 1]
        > the "bool" information has diseappeared !!

        This is strange, indeed. It deserves a message in the Caml List or
        at Caml bugs.

        --
        Daniel de RAUGLAUDRE
        daniel.de_rauglaudre@...
        http://cristal.inria.fr/~ddr/
      • Remi VANICAT
        ... It look like you are trying to do something similar to phantom type, so you may be very interested by the following :
        Message 3 of 3 , Oct 18, 2002
          Julien Cohen <jcohen@...> writes:

          > Hello, I'm trying to manage with constructed types in a particular way,
          > can anyone tell me if it is a "really bad" way?

          It look like you are trying to do something similar to phantom type,
          so you may be very interested by the following :

          http://caml.inria.fr/archives/200109/msg00097.html

          well, this add something to what you are trying : opaque polymorphism.

          >
          >
          > I want to use 'a lists with an additionnal type information : 'b.
          > Here is the type declaration: (ocaml 3.04)
          >
          > # type ('a,'b) t = 'a list;;
          > type ('a, 'b) t = 'a list
          >
          > I have a cons:
          >
          > # let f (x:'a) (y:('a,'b) t) = (x::y : ('a,'b) t);;
          > val f : 'a -> ('a, 'b) t -> ('a, 'b) t = <fun>
          >
          > Then a value :
          >
          > # let (v: (int,bool) t) = [1];;
          > val v : (int, bool) t = [1]
          >
          >
          > The problem is when I do a "cons" on it:
          >
          > # f 1 v;;
          > - : (int, '_a) t = [1; 1]
          >
          > the "bool" information has diseappeared !!
          >

          the problem is that the compiler know that ('a,'b) t = 'a list and use
          this information to make your code more polymorphic. It's a clever
          thing, but it not what you want.

          There is two known solution :

          # type ('a,'b) t =
          | Cons of 'a * ('a,'b) t
          | Nil;;
          type ('a, 'b) t = Cons of 'a * ('a, 'b) t | Nil
          # let v = (Cons (1, Nil) : (int,bool) t);;
          val v : (int, bool) t = Cons (1, Nil)
          # Cons (1, v);;
          - : (int, bool) t = Cons (1, Cons (1, Nil))

          Here I'm redefining a list type. The problem is that you wont be able
          to use the stdlib List operation.

          then there is the module solution, using abstraction to forget the
          type information :

          # module type TTYPE =
          sig
          type ('a,'b) t
          val empty : ('a, 'b) t
          val f : 'a -> ('a, 'b) t -> ('a, 'b) t
          val to_list : ('a, 'b) t -> 'a list
          end;;
          module type TTYPE =
          sig
          type ('a, 'b) t
          val empty : ('a, 'b) t
          val f : 'a -> ('a, 'b) t -> ('a, 'b) t
          val to_list : ('a, 'b) t -> 'a list
          end
          # module T : TTYPE =
          struct
          type ('a,'b) t = 'a list
          let empty = []
          let f x y = x :: y
          let to_list x = x
          end ;;
          module T : TTYPE

          then :
          # let v = (T.f 1 T.empty : (_, bool) T.t);;
          val v : (int, bool) T.t = <abstr>
          # T.f 1 v;;
          - : (int, bool) T.t = <abstr>

          the problem here is that the type t become abstract : you can't use
          stdlib function on it without using the to_list function.

          You may want to define some other function on it to be able to use
          your type information more easily.

          --
          RĂ©mi Vanicat
          vanicat@labri.u-bordeaux.fr
          http://dept-info.labri.u-bordeaux.fr/~vanicat
        Your message has been successfully submitted and would be delivered to recipients shortly.