Thursday, June 1, 2006
Refactoring code is a necessary thing. Unless you work in some very specific environment where casual refactoring is not allowed (like in some safety-critical applications where the most minute change has to be pondered upon by teams and committees for weeks), you cannot code perfectly on the first shot.
More often, you end-up reviewing code and making it clearer, merging parts that are too similar, removing what turned out not to be useful, cleaning up the names, moving things around, etc… there are dozen of refactoring cases that usually help remove the stink out of it.
One self-inflicting problem I’ve often been confronted to is over-engineering: I tend to over-think, over-design and over-anticipate.
Sometimes it’s good to just spend time trying to make your code more modular and as future-proof as you can, but often, it leads to code that has no real use right-now, and that ends up having to be modified because when you need it, it’s not in the form you’ve implemented it originally.
This is an Extreme Programming practice aptly named You Aren’t Gonna Need It.
A classic example of YagNi that I am paying dearly is a large application I’m working on at the moment (at least large from the perspective a single developer).
It’s a fairly complex database application with an equally demanding winform GUI layer in C# on top.
I built the GUI in a very modular fashion: each bit of information that could be grouped has its own User Control, sealing its particularities.
Then each of these controls is used in panels that embody another layer of functionality.
Each panel is then loaded as needed into a form that display the panels on demand.
The issue is that I now have to make major changes to the application and there are too many layers in these controls, making code hard to change.
I had built it this way for re-use, thinking that it could be useful to have independent specialized controls, say for entering addresses, or customer details, etc.
Well, each of these controls took me a lot of time to craft, trying to make them as independent upon my particular implementation as I could. It turns out though that I’ve used each control no more than once -maybe twice for a couple- in the whole of the application, and I now realize that it’s unlikely that I would get another job that would require the exact same user-interface broken down the exact same way.
So my uber-GUI controls are mostly a waste of time and complexity.
I should have simply created the forms directly, using partial classes (a new .Net 2 feature) to separate each logical part into something manageable.
My application would have been faster to develop and faster to run, with a lot less of unnecessary layers of abstraction.
I’m having a hard time with that, but I’m getting better, hopefully…