Wednesday, July 01, 2009

Design patterns in Scala: Adapter

One might think that when considering Adapter pattern the ol' good Java implementation is 'as good as it gets'. But as you're probably already guessing I believe it is not. Surprisingly (ye.. right) Scala shines also on this front.

Say the code we're dealing with is:

class Communism { def makePropaganda = ... }

class Capitalism { def usePublicRelations = ... }

If you wanted to adapt 'Communism' to behave as 'Capitalism' (say we need it during visits of important foreign ministers ;)) in Java typically you'd do it like:

That may seem like a one simple and insignificant improvement - but in fact it's pretty powerful stuff. After all an explicit conversion you did in Java is nothing but noise (by now you most probably noticed that Scala is the noise-annihilator). Also it saves you from all that extra keystrokes and postpone RSI ;).

And with more difficulty it gets only better. Consider following problem:

For reasons unknown (Architectus Reloadus asked us to do so) we want to extend some lists in our system with a 'fancyMethod'. These conversion should apply only to the lists that contain elements able to be converted to a 'String'.To do it in Scala you implement an implicit conversion of a 'listToStringList' and put a requirement on a user of providing an implicit conversion of each element to 'String'.

I won't provide the Java solution for this problem just because I care about my sinews..

An important thing to remember is that implicit conversions in Scala are not transitive. It is still possible to do such conversion (with calling any method explicitly) but it must be 'requested' with ':' operator.