Sunday, March 11, 2007
Unit Testing FizzBuzz? Are You Out Of Your Fucking Mind?
One blogger cooked up an implementation of FizzBuzz in Java which gives you the option of changing everything -- the rules, the terms displayed in the text, the language, everything.
My FizzBuzz was intended to be sarcastic, but this should have been the real target of my sarcasm. My solution is something like fifteen lines of code. This solution comes in a .zip file with documentation, DEFAULT_XYZ variables, and unit tests. The comments are more than fifteen lines!
This solution does not have any significant advantage in flexibility over my own quick joke version, and its absurd, painfully detailed documentation is infinitely less clear. Not only that, the "one little flaw" that the author writes off as inconsequential is that you can't change the numbers FizzBuzz alters its output for. That is to say, if you want to do a FizzBuzz that puts out new strings on multiples of 7 or 2, it just can't be done without dismantling the entire system. Except the whole point of FizzBuzz, in reality, is to teach children to recognize numeric patterns in sequences. The numbers involved are the only interesting thing. And a system this overblown takes a hell of a long time to dismantle.
Honestly, you have to wonder. This FizzBuzz is so nightmarishly awful, such a monument to useless busywork, and the blogger's reasoning so flat-out bad, I'm tempted to think the whole thing's a fake -- a troll from some Rails hacker who wants to revive the "Ruby vs. Java" blog war from last year.
I really shouldn't post before breakfast. I'm always grumpy before breakfast. Last time I posted before breakfast, I got myself kicked off a mailing list. I'm sure when I go back and look at this in a less fiendish frame of mind, I'll see advantages to this approach. On the other hand, I posted a little while back that hiring somebody who's willing to code FizzBuzz is as bad an idea as hiring somebody who's unable to code FizzBuzz, and this is pretty much exactly what I was talking about.
Life is short, and this is as true for business models as it is for human beings. Don't believe me? Ask Microsoft. Or better yet, wait five years, and then ask Microsoft, and watch how quickly those five years went. Ask Microsoft what they spent those five years doing while their business model died its death.
You need to be flexible and adaptable in business. This Java solution packs layers of beauraucracy onto what might be the simplest programming problem in the world. Layers of beauraucracy have the functional result of impeding change -- consider how my solution, you can change anything, whereas the Java one supports some changes and not others, and the developer's assumptions about what changes may or may not be necessary shape the eventual range of what changes are possible.
But the sociological result of layers of beauraucracy is the real danger here. Sociology is much more important to software development than people generally realize. The sociological effect of Java, in this case, is encouraging conformity and limiting imagination. The reason is simple: conformity and limited imagination are necessary for the kind of person willing to go through all that effort just to solve FizzBuzz, and cover every reasonable variation. And the key there is not the thoroughness -- thoroughness is admirable. The key is the term "reasonable." The term "reasonable" is an utterly dangerous term. It is by nature a value judgement, and a conservative value judgement. "Reasonable" and "innovative" are not synonyms. Think of all the unreasonable features on the iPod. You can't even change the battery! No reasonable person would ever have designed that thing, which is why one of the most famously unreasonable people in the world is taking over the music industry.
Anybody who's ever seen a software project fail or even falter knows that if you cover every reasonable variation, you're going to build a whole lot of options that your client or users will never ever use or even see, wasting time and money in the process, while at the same time building something which can bend at every join except the one they need to flex. You shouldn't cover reasonable variations. You shouldn't cover any variations. You should code the quickest, simplest solution you possibly can, even if it looks stupid as fuck, and then if your client or your users need some change, you should choose the way to do it which requires the absolute minimum of work.
Everybody pretends they already know this, but if you really mean it, you have to ultimately realize that spinning your wheels writing unit tests for FizzBuzz is not good training for the process of writing great software. Everything you do shapes your mind. I have professional training in hypnosis and I assure you, literally everything you do shapes your mind to some extent. If you're going out there and practicing something as reasonable, safe, and useless as writing tests for FizzBuzz, the next time you sit in front of a computer, you'll do something reasonable, safe, and useless. The powerful pattern-recognition machine that is your subconscious mind will say, "a-ha! I'm in front of a computer. That means it's time to write unit tests for FizzBuzz!"
Don't do it! It's bad!
The point of unit testing isn't covering your ass. It's making code succinct. Unit testing is a design tool. Unit testing FizzBuzz is like drawing up blueprints when you need to make a sandwich.