Version française
Home     About     Download     Resources     Contact us    
Browse thread
Duplicate functionality?
[ Home ] [ Index: by date | by threads ]
[ Search: ]

[ Message by date: previous | next ] [ Message in thread: previous | next ] [ Thread: previous | next ]
Date: -- (:)
From: Jacques Garrigue <garrigue@m...>
Subject: Re: [Caml-list] Duplicate functionality?
From: "Stephen Brackin" <stephen.brackin@verizon.net>

> My biggest initial question is why OCaml has both a modules system and
> objects: Aren't they different ways of accomplishing the same things?

I'm not aware of any detailed comparison between objects and modules
in ocaml. However I'll try to give my thoughts on that.

Both modules and object have multiple roles, and they only overlap
for some.
For instance, modules offer some kind of namespace management, which
objects do not. This is different from Java which has no modules, and
where classes have a role in namespace management.
Similarly object subtyping allows the creation of heterogeneous
collections of values, which is impossible with modules.

Another specificity of objects is their extensibility through
inheritance, with late binding (i.e. components can depend on each
other.) You can try to do this with functors and recursive modules,
but this quickly becomes rather heavy-weight.

The real overlap between the two concepts is in their ability to
create collections of methods, and to have parameterized constructors
(functors for modules). 
Indeed, apart of the capacity to hide types, one could argue that
objects alone can encode the whole module system, thanks to
polymorphic methods. Practice shows that it ends up being rather
clumsy: type parameters can only be expressed by type variables, which
do not behave exactly like type constructors.  Moreover object typing
relies strongly on type inference, which can cause confusing error
messages.
Encoding objects into modules, as abstract data types, generally works
well, but you lose object subtyping, and you must specify the module
name for each method call (a light burden in general, but not so nice
when using functors, and you end up with lots of module names around.)

So yes, one could say that objects and modules provide different ways
to do some similar things. This is particularly true for simple data
structures like stacks or queues: there is no good reason to use one
approach over the other.
In practice they provide very different tradeoffs between flexibility
and robustness. Modules are extremely robust, in that you are so
explicit that the origin of any problem should be immediately
clear. But this also means more verbosity, and some difficulties in
reuse: you may have to parameterize on more modules than you
would like to.  On the other hand objects let you pass your
implementation around with your data, making things much simpler at
first. But their typing being more brittle, it can hurt when something
goes wrong.

Since one uses ML mostly for robustness, I suppose that when there is
no explicit need for subtyping or late-binding, the natural way to go
is modules. But when they become so verbose as to be cumbersome, and
the underlying model is object-oriented, objects may be more
comfortable. 
Both approaches expose their weaknesses when pattern-matching is
involved: this essential feature of functional programming doesn't
like any form of abstraction.

By the way, I believe there is one further hurdle when using objects:
their definitions are not compositional. That is, a module is just a
collection of functions, which can exist themselves independently from
one another (yet not independently of type defintions), but methods
are not just functions (for instance you cannot pass the complete self to
a function), and they cannot exist independently from objects. This
makes harder the transition from the core language, where one usually
starts writing, to the object language, where one might want to move.

Jacques Garrigue