Suppose that we define an interface like this:
interface Hashable {
int hash();
}
Now we can make classes that implement this interface. For example a List class:
class List<T> : Hashable {
int hash(){
int h = 0;
foreach(x in this){
h = combineHash(h,x.hash());
}
return h;
}
}
The problem is that we call hash on elements inside the List<T>, so T has to be Hashable. So we have to do:
class List<T : Hashable> : Hashable {
... same here ...
}
On the other hand, we also want to be able to construct lists with elements that are not hashable. In that case we simply don’t want List<T> to implement Hashable. So:
List<AHashableType> is itself Hashable
List<NotAHashableType> is not Hashable
Furthermore, we want the hash method to be polymorphic (the OO kind of polymorphic, not parametrically polymorphic). So if we construct a List<Foo> with Bar‘s and Baz‘s inside, where Foo is Hashable and Bar and Baz are subtypes of Foo with different hash() methods, then that List<Foo>.hash() should call the right hash method at runtime.
This seems like a basic thing that languages should be able to express. The same pattern comes up in different cases, for example with ToString() and with IComparable. So far I haven’t found a language and a solution in that language that lets me express this in a type safe way. Do you know of such a language and a solution in that langauge? Haskell comes quite close with its type classes, but unfortunately these are dispatched at compile time.
I think it’s useful to separate the two issues you’ve described. The first is conditionally implementing an interface. Like you said, Haskell type classes do this. It would look something like:
The second issue is OO polymorphism, which you can mimic in Haskell with a function-pointer-like mechanism.
I’ve read a couple papers that add this sort of “conditional interface implementation” to a Java-like language. One of them is JavaGI (http://homepages.cwi.nl/~ralf/JavaGI/), which also adds the ability to implement an interface for a data type that you didn’t originally define (like Haskell type classes). I can’t remember what the other paper was called.