How to create the IntSet type with core? [joke]

Francois Berenger francois.berenger.working at gmail.com
Mon Nov 12 08:51:19 GMT 2012


I think this google group should be renamed to: ocaml-type-junkies
;)

On Friday, November 9, 2012 6:11:14 PM UTC+9, David House wrote:
>
> There is already an Int.Set module! :) 
>
> Here is a five-minute guide to the set / map / hashtable setup inside 
> core. I'll use the example of hashtables, but the language readily 
> translates into sets / maps. 
>
> There are two types of hashtables in core. Ones that use polymorphic 
> comparison, and ones that use a specific comparision function that is 
> hopefully more efficient and has non-surprising semantics (we 
> basically think polymorphic comparison, despite its convenience, is 
> too surprising to be an overall good thing). 
>
> The type of hashtables using polymorphic comparison is ('key, 'value) 
> Hashtbl.Poly.t. The type of hashtables using, e.g., int comparison for 
> the keys is 'value Int.Table.t. Given the previous paragraph, you 
> should always try to use Foo.Table when you can. 
>
> When you create a hashtable (e.g. using [create], [of_alist], or 
> [t_of_sexp]), you must use the specific module name. I.e. [let table = 
> Int.Table.create () in]. However, when you already have a hashtable in 
> your hands, and you want to use accessor functions, you should just 
> use Hashtbl.foo, regardless of what comparison function it uses. 
>
> To translate into Maps and Sets: 
>
> 'value Foo.Table.t  ('key,'value) Hashtbl.Poly.t  Hashtbl.foo 
> 'value Foo.Map.t    ('key,'value) Map.Poly.t      Map.foo 
> Foo.Set.t           'element Set.Poly.t           Set.foo 
>
> -- 
>
> If you have your own type and want to make Table, Map and Set 
> submodules, it's really easy: 
>
> module T = struct 
>   type t = ... with compare, sexp 
>   let hash = (* your hash function, maybe Hashtbl.hash *) 
> end 
> include Comparable.Make(T) 
> include Hashable.Make(T) 
>
> Saying "with compare" generates you an efficient comparison function 
> specialised to your type. (Note that all component types need to have 
> comparison functions defined too, whether through "with compare" or 
> through primitives.) The Comparable.Make functor adds in modules to 
> make you satisfy the Comparable.S signature (basically the Set and Map 
> modules, and a few more). The Hashable.Make functor adds in modules to 
> make you satisfy Hashable.S (basically Hashtbl, as well as some others 
> like Hash_set). If you don't want the Hashable stuff, there is no need 
> to define a hash function. (Although Hashtbl.hash is normally not a 
> bad choice.) 
>
> -- 
>
> Here's how this all works under the hood: 
>
> The type of maps is "really" ('key, 'value, 'comparator) Map.t. Maps 
> contain in their values the function that is used for comparing keys, 
> i.e. a function of type 'key -> 'key -> int. But what is this 
> "comparator" thing? 
>
> We can first motivate things by saying: it's a pain to have to type 
> Int.Map.find for int-maps, String.Map.find for string-maps, etc. etc. 
> It'd be nice to have a single type and use Map.find for everything. 
> But this presents a problem because of functions like Map.merge, which 
> takes two maps and combines them. You need to know that the comparison 
> functions are identical, but how can you do this? 
>
> So we have this extra comparator phantom type. Nothing in the actual 
> representation has a type involving 'comparator: it's just for static 
> checking. If you want to have a new comparison function, you must mint 
> a new comparator type. (Including the Comparable signature does this 
> for you.) 
>
> I originally wrote this last section with hashtables in mind, but it 
> appears that hashtables work slightly differently: they just assert 
> that the hashing functions are physically equal inside [merge]; you 
> don't get a compile-time error for something like [Hashtbl.merge 
> (Int.Table.create ()) (String.Table.create ())]. 
>
> On Fri, Nov 9, 2012 at 8:14 AM, Francois Berenger 
> <francois.ber... at gmail.com <javascript:>> wrote: 
> > Hello, 
> > 
> > I'm converting some standard code to use core. 
> > 
> > How do I do this in core: 
> > 
> > module IntSet = 
> >   Set.Make 
> >     (struct 
> >       let compare = Pervasives.compare 
> >       type t = int 
> >     end) 
> > 
> > Thanks a lot, 
> > F. 
> > 
> > PS: yes, I opened Core.Std and did not die from it. ;) 
> > 
>
-------------- next part --------------
An HTML attachment was scrubbed...
URL: <http://lists.ocaml.org/pipermail/core/attachments/20121112/6209c199/attachment-0001.html>


More information about the core mailing list