Mark Needham

Thoughts on Software Development

Coding: Wait for the abstractions to emerge

with 3 comments

One of the things that I’ve learnt while developing code in an incremental way is that the way the code should be designed isn’t going to be obvious straight away so we need to be patience and wait for it to emerge.

There’s often a tendency to pull out classes or methods but more recently I’ve been trying to follow an approach where I leave the code in one class/method and play around with/study it until I see a good abstraction to make.

More often than not it takes a few times over multiple days before anything reveals itself.

I recently watched Venkat Subramaniam’s Agile India presentation ‘How to Approach Refactoring‘ in which amongst other bits of advice he suggests that we ‘make it work then make it evolve‘ which sounds like it’s covering the same type of ground.

Sometimes in the rush to abstract code to make it easier to test or to reduce the size of a class we end up creating an abstraction which doesn’t really make sense in the business domain.

Having big methods of inline code goes against what we’ve learnt but putting all the code together makes it much easier to see the real abstractions in the code than if some premature abstractions have been made and we have to remember those as well.

It’s still useful to be driven by the goal of pulling out small classes of behaviour/data that are easy to test but spending a bit more time understanding the domain before doing so seems to work better.

We recently had some unwieldy code which we couldn’t quite work out how to abstract so we left the logic inline until we knew better even though it looked quite messy.

Eventually when talking to one of the subject matter experts they mentioned a term that they used which actually combined two things together which we’d originally thought were independent.

A simple rule of thumb is that if there is no name in the domain for what you’re abstracting then it might not make sense to do so.

It doesn’t always work but at least gets your thinking about whether you’re improving the code with the abstraction you’re about to make!

Written by Mark Needham

March 17th, 2012 at 11:19 am

  • Jeff Doolittle

    Good advice.  It is always tempting to fall into the trap of “premature abstraction”.  I follow a similar approach – make it work before worrying about abstractions and potential for reuse.  

    I find that in many cases, the best abstractions come about by not DRYing up my code too soon.  Typically my most useful abstractions come about when I have 2 or 3 concrete implementations that have similar characteristics, and from there I draw out an abstraction.  If I DRY up too soon, later on I often find that either my abstraction is too restrictive (doesn’t fit enough concrete implementations) or leaky (underlying details must be exposed in order to allow implementers or clients of the abstraction to work with it effectively).

  • http://twitter.com/flowchainsensei Bob Marshall

    In a nutshell then “embrace (the likelihood of) change”?

    - Bob

  • http://richhewlett.com/ Rich Hewlett

    Great post. I happen to be following this approach at the moment. I’ve found that I’m creating ugly procedural code initially but then as it evolves the natural abstractions are appearing. Once the basic flow is in place I will refactor the hell out of it!