Summary
There are many different "[insert-buzzword-here] Driven Design" methodologies, i.e. Policy Driven Design, UI Driven Design, Data Driven Design. I would like to propose a new one: "Implementation Driven Design".

Advertisement

Previously I referred to an approach that I used for arriving upon a Bank Account design ( See my entries titled, OOP Case Study: The Bank Account Class Part 1, Part 2 and Part 3 ) as a bottom-up approach. I think by using the more descriptive term "Implementation Driven Design" it helps describe more the approach I am advocating.

The basis of Implementation Driven Design ( or IDD ) is built upon the core assumption that software requirements are rarely complete nor static. As much as I would love to force clients to completely specify their requirements before I start implementing their software, this never occurs. Being in the business of writing software, it is my job then to make them happy. The common response I hear from programmers is to gripe about how the customer is a moron, or something to that effect. This doesn't hold water for me. Sometimes I am my own client, and no matter how hard I try, even I can never know in advance exactly how my own software is going to turn out in the end. I envy those who work with a static software specifciation, programming must be so much easier.

The purpose of IDD is to make every part of the software as reusable as possible. This is done by avoiding overspecifying the role of any component of the software. If at any point a function or class is too specific, I refactor it into more reusable components. This approach is counter-intutitive, because at first it appears to take more time and effort to write reusable components. As a project continues and the requirements inevitably evolve, this approach pays off enormously. Since I started using IDD, I actually have a very large reusable code base, which has paid for the extra original effort required several times over.

This approach has a wonderful side-benefit of implicit testing. If a portion of code is reused significantly, then every time it is run it is tested again and again. Part of the goal of IDD is to write classes and functions that are so simple, so as to be easily verified upon simple inspection and rarely need modification. If at any point a change is required, I look for new opportunities for refactoring and often find some.

The reason I am calling this approach Implementation Driven Design is because of the goal of reusable components, I now think about software more from the ground up in terms of the components needed to eventually represent the abstractions present in the software. I don't trust the details at the highest level of abstraction to remain consistent, but I do trust that the tools needed won't vary.

This brings me back again to the Bank Account class. In the absence of specific details,
I know that any implementation of a Bank Account is going to do the following two things:

view balance

modify balance

The next specification is that likely it will be multithreaded, therefore I will need

lock

unlock

Another specification that it likely going to want to log transactions

view transaction history

apply transaction

Finally yet another specification that makes a lot of sense:

getting the balance at a specific date

Many programmers / architects try simply to anticipate all of these specializations and start by writing a single perfect class which incorporates all of them. This is often an iterative process that involves rewriting over and over the class as specifications change or get added. The IDD approach is to start from the ground up writing four separate classes, each one using or inheriting from the previous. What is perhaps unclear here, is how I arrange these specifications in some kind of order. This comes with experience, and thinking about what a logical sequence of classes are. Clearly in any kind of hierarchy we want to start with the most non-specific class as the root. This is the most reusable case, and the simplest to implement or describe.

I should point out that a pitfall that must be wary of with IDD is to avoid overspecifying the general purpose classes. It is tempting to include lots of useful functionality in a class that we want to see reused. We have to keep in mind that the kind of reuse we want to encourage is that of the definition of new types or the writing of new functions. We can't get caught up early on trying to anticipate every possible change, we need instead to make it easy for other to adapt our solution to their needs.

The IDD approach is in large part the philosophy that we see embodied in the C++ Standard Template Library (STL). The STL was designed not to anticipate every possible use, but rather to be general enough as to be useful as a basis for our new types and algorithms which are specific to the problem domain.

I think the only big obstacles to IDD is what I perceive as a generalized fear to specialize existing types, or to design new types for specialization. I want to encourage programmers to break out of their shell, and start generalizing more.

Talk Back!

Have an opinion?
Readers have already posted
2
comments
about this weblog entry. Why not
add yours?

RSS Feed

If you'd like to be notified whenever Christopher Diggins adds a new entry to his weblog, subscribe to his RSS feed.

About the Blogger

Christopher Diggins is a software developer and freelance writer. Christopher loves programming, but is eternally frustrated by the shortcomings of modern programming languages. As would any reasonable person in his shoes, he decided to quit his day job to write his own ( www.heron-language.com ). Christopher is the co-author of the C++ Cookbook from O'Reilly. Christopher can be reached through his home page at www.cdiggins.com.