[Haskell] Per-type function namespaces (was: Data.Set whishes)

Andre Pang ozone at algorithm.com.au
Sat Feb 28 15:15:02 EST 2004


On 28/02/2004, at 3:26 AM, David Bergman wrote:

>> Writing "function expression
>> ..." would work too, but then it looks like a standard
>> function call rather than a function call associated with a
>> particular type, and I think that causes more confusion.
>> Long-time Haskell users understand that writing "foo.f"
>> means "use f in namespace foo"; changing around the language
>> semantics to mean that "f foo" now means "use f in namespace
>> foo" would make lots of people rather unhappy :).
>
> I would want it to look as an ordinary function.

I don't know if I'd want it to look as an ordinary function, because 
then it looks and acts exactly the same as every single other function, 
and it clearly isn't.  As an example of why, look at the API for IORef: 
in my fantasy world, if I were able to write 'readIORef myRef' as 
'myRef.read', I definitely do not want a top-level 'read' function to 
be defined.  Not only does it pollute the default namespace 
unnecessarily, but in this case it actually does conflict with an 
already-existing read function, so what is the type of read now?  read 
has always been the function that's associated with the Read type 
class, but the name of 'read' for the IORef accessor clearly also makes 
sense.  They are clearly two different functions, and I would wish for 
them to stay that way.

> The single biggest problem
> with Haskell, in my extremely humble opinion, is the shared namespace 
> for
> all data type accessors, with which you probably agree. It is what 
> irritated
> me the most with Entity-Relationship Diagram, that all fields need to 
> have
> unique name globally. This in contrast to instance variables, methods 
> and
> general overloading, as often found in OO languages.

Right, I completely agree that the shared namespace for data type 
accessors is the core of the problem, which is what led to me discuss 
the scheme I had in mind.  I think the community, too, realises this 
problem is more than just an annoyance: at the 2003 Haskell Workshop, a 
new labelled fields (record?) system was being discussed, and there was 
much nodding when somebody stated that they'd be entirely happy keeping 
the current labelled fields system except that they wanted to be able 
to use the same field name for different data types.  So, such a system 
effectively provides individual namespaces per data type, which is 
similar to my goal.  However, because labelled field selectors operate 
directly on the data type they're defined on, they are unsuitable to be 
exported as a accessor function to an outside module, because they 
provide direct access to the internals of the data type rather than 
abstracting that away via a function.  However, what I'm after is 
exactly the same goal as yours.

Thank you for bringing in the name 'accessor', by the way -- it's much 
nicer than writing 'per-type function' :).

>>> "mere" intranamespacial parameter type
>>> lookup (regular overloading) would achieve the same effect, without
>>> the
>>> (implicit)
>>> namespaces?
>>
>> I'm not sure what you mean by "intranamespcial parameter type lookup"
>> -- can you explain?
>
> ah, I meant regular overloading, i.e., have a function be identified 
> not by
> its name, but by its whole signature, including the arity and parameter
> type(s) [yes, curry, curry...]

Sure, overloading can do exactly what we want (and Oleg has proven it 
with the sample code he's pasted).  I am quite happy if type classes 
are capable of modelling such a scheme, although there must be some 
support from the compiler so that one doesn't have to manually declare 
a type class + various instances for each accessor you'd want to write. 
  One thing I am a bit worried about using the current type class 
mechanism to do such a scheme is that you still clutter the global 
namespace (see a few paragraphs up about readIORef for why).

>> I (think I) understand the difference between dynamic binding vs
>> overloading: here, all I'm after is trying to use the type
>> system to give us a very simple form of overloading (e.g.
>> based on the first argument to a function), that gives us the
>> same effect as a per-type name space.
>
> When I read my own response, I know realize that it sounds harsh. Sorry
> about that. That was not the intention. I also think you understand and
> appreciate the difference between the two forms of polymorphisms.

No offense taken; if anything, you are making me think harder about the 
problem I'm trying to solve and whether the way I'm going about it is 
right (or has been done before).

> You touch at one of the core problems of Haskell.

Glad to see somebody else agrees.  Oddly enough, the more I discuss 
this problem, the more I'm convinced that the approach I've suggested 
is the ideal way to go about it--implementation details being a minor 
detail, of course ;).  What I'm secretly hoping is that the 
GHC/hugs/HBC people will see what I'm trying to achieve, tell me I'm 
totally nuts, and then suggest an alternative, much simpler approach 
which gives us exactly the same goal ...


-- 
% Andre Pang : trust.in.love.to.save



More information about the Haskell mailing list