Polymorphic variants question
[
Home
]
[ Index:
by date

by threads
]
[ Message by date: previous  next ] [ Message in thread: previous  next ] [ Thread: previous  next ]
[ Message by date: previous  next ] [ Message in thread: previous  next ] [ Thread: previous  next ]
Date:   (:) 
From:  Jon Harrop <jon@f...> 
Subject:  Re: [Camllist] Polymorphic variants question 
On Friday 01 September 2006 18:31, David Allsopp wrote: > let f x = if x = `A then (true, `B) else (false, x);; You probably want: # let f = function `A > true, `B  `C > false, `C;; val f : [< `A  `C ] > bool * [> `B  `C ] = <fun> > then I get a type error unless I change > (false, x) > to > (false, id x) Use coercion :> instead of an adhoc function: # let (f : [`A  `C] > bool * [`A  `B  `C]) = fun x > if x = `A then (true, `B) else (false, (x :> [`A`B`C]));; val f : [ `A  `C ] > bool * [ `A  `B  `C ] = <fun> > Is there a better way of writing this? I'm using this in the context of > several interrelated lexers where `A, `B and `C are highlevel states and > certain lexers can only be called in a subset of those states but each > lexer may yield any value for the nextstate. I'd quite like to eliminate > the id x bit since it's only there to "separate" x from the return value > for the typechecker. Note that the type of your id function is not 'a > 'a: # let id = function `A > `A  `C > `C;; val id : [< `A  `C ] > [> `A  `C ] = <fun> So it accepts a subset of {A, C} and returns a type that unifies with any superset of {A, C}. To leverage static type checking you must provide as much information as possible to the static type checker. In this case, rather than using "if" to denote `A or not `A, you can just as easily use pattern matching to imply specifically `A or `C.  Dr Jon D Harrop, Flying Frog Consultancy Ltd. Objective CAML for Scientists http://www.ffconsultancy.com/products/ocaml_for_scientists