Monthly Archives: August 2007

Decisions

Everything you do has two parts: the decision making and the manual labor. For example, when you are coding, you first decide what you want to write and then you type it. Often the two parts are so intertwined that it is not practical to separate them, other than conceptually. When you start typing a function you rarely know exactly what you will write. Instead, you continuously make small decisions as you go.

The decisions are the important part. A well-trained Neanderthal could do the typing. But to do the right decisions you need skill and experience.

An obvious way to improve productivity, then, is to add the number and impact of decisions. There are a number of ways:

  1. To give more room for decisions, reduce the time spent on manual labor. This is the virtue of laziness, as popularized by Larry Wall:

    Laziness: The quality that makes you go to great effort to reduce overall energy expenditure. It makes you write labor-saving programs that other people will find useful, and document what you wrote so that you don’t have to answer so many questions about it.

  2. Many decisions are not important but they have to be made. Naming conventions are a good example: when choosing between CamelCase versus ALL_CAPS in constant names, the actual choice doesn’t matter as long as one of them is used consistently. To improve the impact of each decision, let someone make these less important choices for you. Use an existing pattern, or a framework that has reasonable defaults. David Heinemeier Hansson thinks this was one of the main reasons for Rails’ success. Rails has made the choices so you don’t have to:

    Rails is opinionated software. It eschews placing the old ideals of software in a primary position. One of those ideals is flexibility—the notion that we should try to accommodate as many approaches as possible, that we shouldn’t pass judgement on one form of development over another. Well, Rails does, and I believe that’s why it works.

    With Rails, you trade flexibility at the infrastructure level to gain flexibility at the application level. If you are happy to work along the golden path that I’ve embedded in Rails, you gain an immense reward in terms of productivity that allows you to do more, sooner, and better at the application level.

    […]

    One characteristic of opinionated software is the notion of “conventions over configuration.” If you follow basic conventions, such as classes are singular and tables are plural (a person class relates to a people table), you’re rewarded by not having to configure that link. The class automatically knows which table to use for persistence. We have a ton of examples like that, which all add up to make a huge difference in daily use.

  3. Distribute decision-making. If a tech lead makes every decision by himself, he ends up using his valuable developers as Neanderthal typists. The better way is to push the decision making down to the developers. They have the best understanding of the code base. If they also have an easy access to customers they are in the best place to make many of the decisions.

And after writing this, I now realize these are all instances of the same advice: make each decision only once. Essentially, I just repeated the DRY principle three times. Ironic, isn’t it?

In the search for discipline

poker.png

I played poker online last night. It was my first time in a long time. I played aggressively and was able to win quite a few big pots and steal some smaller ones. By the end of the session I had won a few dollars, but it could have been much more. My mistake was the usual one: I didn’t fold nearly often enough.

Poker is an art of discipline. Good players know when to fold. They avoid expensive mistakes.

Software development is an art of discipline too. As Scott Koon put it:

Every month a new programming language or methodology appears, followed by devotees singing its praises from every corner of the Internet. All promising increases in productivity and quality. But there is one quality that all successful developers possess. One trait that will make or break every project.

Discipline.

An undisciplined developer will not be able to ship on time and will not write code that is easy to maintain. A disciplined developer will not only enable the success of a project, but will raise the level of productivity in others. Software architects and developers do themselves a disservice when they attribute their success to whatever methodology they have adopted. It really boils down to how disciplined you are.

So how to become disciplined? How to bring discipline into your team?

Jeff Atwood suggests that new developers should be mentored by a discipline advocate. The advocate would keep reminding the developers about the value of discipline.

An excellent suggestion. But Jeff’s reference to Full Metal Jacket doesn’t make it sound very fun. Do we need to crack the developers to teach them discipline? Is discipline so unpleasant?

No!

Think of poker. The best players do not dislike discipline. They love it, because they know it’s what separates them from losers.

Sometimes though you see a good poker player lose his discipline. Perhaps he just lost a lot of money to a worse but luckier player. He becomes frustrated and starts playing recklessly. Frustration feeds indiscipline.

In learning discipline, poker has an advantage over software development. There is a tight (albeit noisy) feedback loop between your actions and your performance. Players see again and again how playing loose costs them money.

The natural feedback in software is slower. It may take months for a problem to surface, and when it does, linking a symptom to the cause may be difficult. Worse yet, the original developers may have already moved to other projects, and miss the valuable experience.

One way to tighten the feedback is (as Jeff suggested) to give regular feedback to developers via code reviews and such. An obvious goal is to prod new developers to the right direction. But there’s another, perhaps even more important consequence.

Regular feedback gives a sense of meaning to developers’ work. Feedback-less coders lose motivation and become frustrated. And frustration feeds indiscipline.

The consequences of lack of discipline grow toward the end of the programs life cycle, maintenance. To learn the outcome of indiscipline, novice developers should maintain code at some early point of their careers. Since maintenance work tends to focus on the worst parts of the code, it can be hairy even on good projects. Most often maintainers make changes to undocumented spaghetti code, and hopefully learn a lesson.

Methodology matters. So does technology. Many parts of the development process can be automated. Doing them by hand can be very frustrating. Choosing a sensible technology allows you to focus your discipline on fewer parts of the process. The perceived friction of a wrong process causes frustration in the developers. Frustration feeds indiscipline.

To summarize, here’s my recipe to promoting discipline:

  1. Give honest regular feedback to developers.
  2. Ensure novice developers do maintenance work at some point.
  3. Use technology and practices that make sense to developers.