caml-list - the Caml user's mailing list
 help / color / mirror / Atom feed
* Re: Constructed types
@ 1999-01-21 15:37 Toby Moth
  0 siblings, 0 replies; 4+ messages in thread
From: Toby Moth @ 1999-01-21 15:37 UTC (permalink / raw)
  To: caml-list, Chris.Keane

I remembered this coming up before but have only just found the reference. The question of constructors was raised by Simon Clematide - 20 Jan 97 and answered by Xavier Leroy. Check out the archives for details.

Toby




^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re: Constructed types
@ 1999-01-21 16:05 Markus Mottl
  0 siblings, 0 replies; 4+ messages in thread
From: Markus Mottl @ 1999-01-21 16:05 UTC (permalink / raw)
  To: OCAML

> I remembered this coming up before but have only just found the 
> reference.  The uestion of constructors was raised by Simon Clematide -
> 20 Jan 97 and nswered by Xavier Leroy. Check out the archives for
> details.

Ah, now everything is clear! Read the following page:

  http://caml.inria.fr/caml-list/0030.html

Regards,
Markus

-- 
Markus Mottl, mottl@miss.wu-wien.ac.at, http://miss.wu-wien.ac.at/~mottl




^ permalink raw reply	[flat|nested] 4+ messages in thread

* Re: Constructed types
  1999-01-20 10:42 Chris Keane
@ 1999-01-21  1:22 ` Markus Mottl
  0 siblings, 0 replies; 4+ messages in thread
From: Markus Mottl @ 1999-01-21  1:22 UTC (permalink / raw)
  To: Chris Keane; +Cc: OCAML

Hello,

> then why doesn't this?
> 
>   > # let myfun2 x =
>   >     let m = if x = 0 then (0,0) else (1,1) in
>   >       Bar m;;
>   > The constructor Bar expects 2 argument(s),
>   > but is here applied to 1 argument(s)

I have also come across this problem when porting Okasaki's sources from
SML to OCAML - obviously, this restriction does not apply to SML.

E.g. (taken from a pattern match in function "balance" in the
      implementation of red-black trees):

  | ...
  | body = T body

body should actually be of type tree:

type tree  = E | T of color * tree * elem * tree

But although the preceding patterns already indicate the only possible
type, one cannot just simply match the tuple with one identifier and
place it after the non-constant constructor. One would have to write
something like

  | ...
  | a,b,c,d -> T (a,b,c,d)

I have tried to find something about that in the reference manual, but
found only this (I hope it's relevant):

  The expression ncconstr expr evaluates to the variant value whose
  constructor is ncconstr, and whose argument is the value of expr.

If I interpret this right, a non-constant constructor should work with
any expression (that matches, of course). I don't know, why this does
not apply here.  Since it is possible to do this in SML, I really wonder,
whether there is some special reason to it.

Because it somehow fits into this question, here another problem I have
come across in the same function.

The working version looks like this:

  let balance = function
      B,T (R,T (R,a,x,b),y,c),z,d -> T (R,T (B,a,x,b),y,T (B,c,z,d))
    | B,T (R,a,x,T (R,b,y,c)),z,d -> T (R,T (B,a,x,b),y,T (B,c,z,d))
    | B,a,x,T (R,T (R,b,y,c),z,d) -> T (R,T (B,a,x,b),y,T (B,c,z,d))
    | B,a,x,T (R,b,y,T (R,c,z,d)) -> T (R,T (B,a,x,b),y,T (B,c,z,d))
    | a,b,c,d                     -> T (a,b,c,d)

Now, Okasaki claims that in Standard ML of New Jersey it is possible
to rewrite this as (I use OCAML syntax otherwise and do as if the first
problem presented here did not exist):

  let balance = function
      B,T (R,T (R,a,x,b),y,c),z,d 
    | B,T (R,a,x,T (R,b,y,c)),z,d
    | B,a,x,T (R,T (R,b,y,c),z,d) 
    | B,a,x,T (R,b,y,T (R,c,z,d)) -> T (R,T (B,a,x,b),y,T (B,c,z,d))
    | body                        -> T body

This looks really readable now. But if I do this in OCAML, the compiler
will complain that variables are bound several times in this matching -
they are obviously already bound *before* the multiple match (which is
otherwise possible) is over.

I am not sure whether this feature found in SML/New Jersey creates more
problems than it solves (e.g. what if values bound to the same identifier
have different types in the pattern?). But in this specific function
it comes really handy. At least there doesn't seem to be a good reason,
why names should be bound in other patterns before they can be used on
the right-hand side.

Best regards,
Markus

-- 
Markus Mottl, mottl@miss.wu-wien.ac.at, http://miss.wu-wien.ac.at/~mottl




^ permalink raw reply	[flat|nested] 4+ messages in thread

* Constructed types
@ 1999-01-20 10:42 Chris Keane
  1999-01-21  1:22 ` Markus Mottl
  0 siblings, 1 reply; 4+ messages in thread
From: Chris Keane @ 1999-01-20 10:42 UTC (permalink / raw)
  To: caml-list

If this works as it should:

  >         Objective Caml version 2.00
  >
  > # type foo =
  >     Bar of int * int;;
  > type foo = | Bar of int * int
  > # let myfun x =
  >     let (m,n) = if x = 0 then (0,0) else (1,1) in
  >       Bar (m,n);;
  > val myfun : int -> foo = <fun>

then why doesn't this?

  > # let myfun2 x =
  >     let m = if x = 0 then (0,0) else (1,1) in
  >       Bar m;;
  > The constructor Bar expects 2 argument(s),
  > but is here applied to 1 argument(s)

or even this?

  > # let myfun3 x =
  >     Bar (if x = 0 then (0,0) else (1,1));;
  > The constructor Bar expects 2 argument(s),
  > but is here applied to 1 argument(s)

Thanks,
Chris.

------------------------------------------------------------------- ><> ---
    Hardware Compilation Group, Oxford University Computing Laboratory,
            Wolfson Building, Parks Road, Oxford, OX1 3QD, U.K.
    tel:  +44 (1865) (2)73865      e-mail:  Chris.Keane@comlab.ox.ac.uk
            http://www.comlab.ox.ac.uk/oucl/users/chris.keane/




^ permalink raw reply	[flat|nested] 4+ messages in thread

end of thread, other threads:[~1999-01-21 18:27 UTC | newest]

Thread overview: 4+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
1999-01-21 15:37 Constructed types Toby Moth
  -- strict thread matches above, loose matches on Subject: below --
1999-01-21 16:05 Markus Mottl
1999-01-20 10:42 Chris Keane
1999-01-21  1:22 ` Markus Mottl

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).