Eliminating Comments: the Road to Clarity

I used to think commenting my code was the responsible thing to do. I used to think that I should have a comment for just about every line of code that I wrote. After my first read of Code Complete, my views changed pretty drastically.

I began to value good names over comments. As my experience has increased, I have realized more and more that comments are actually bad. They indicate a failure. In Clean Code Robert Martin says

“The proper use of comments is to compensate for our failure to express yourself in code. Note that I used the word failure. I meant it. Comments are always failures.”

Those are some pretty strong words. You may be reeling back a bit after reading that. It is a normal reaction, but if you’ll drop your defenses for a second, I’ll help you understand why.

Let’s start with an example

Which is more clear to read? This:

int i = 5; // Start at 5, since there are 5 widgets in our production system. // If the number of widgets is evenly divisible by the time, // and we have exactly 5 sockets we need a new one. if ((i % this .t) == 0 && s.Count() == 5) { i++ }

Or:

int currentWidgetCount = DEFAULT_PRODUCTION_WIDGET_COUNT; if (ShouldCreateNewWidget(currentWidgetCount)) { currentWidgetCount++ } private bool ShouldCreateNewWidget( int count) { return CountEvenlyDivisibleByTime(count) && SocketCountAtThreshold(); }

Even though the second example is more code, the code is self-documenting. The names of the variables and methods themselves are telling you what the code is doing.? They are also serving to abstract out the concepts so that you don?t have to think about the entire piece of logic at one time.? This simplifies your code.

In the above example, you don?t have to look at the method ShouldCreateNewWidget.? You can deduce that the flow of that logic checks to see if it should create a new widget based on the count, and if it should it does.

If you want to know how it is determined if a new widget should be created, then you drill into the method, and you can see that if the count is evenly divisible by time and the socket count is at the threshold, then the answer is true, otherwise it is false.

Consider again the first example.? What happens if that logic changes, but the comments aren?t updated?? When you read the comments, how do you know that they are even correct unless you read through and understand the logic anyway?

Why are comments so bad?

It is not that comments in and of themselves are bad.? It?s more that having comments in your code indicates that your code itself is not clear enough to express its intent.? Elegant code should be able to express itself simply and completely.? Comments are not code, they are metadata about the code.? If you want to write elegant code, write elegant code, not elegant prose about code.

Here are some of the major reasons why comments are bad:

They do not change with the code. If a refactor tool changes the code, it cannot change the semantics of the comments, it can only change the syntax where it can recognize keywords.

If a refactor tool changes the code, it cannot change the semantics of the comments, it can only change the syntax where it can recognize keywords. A wrong comment is worse than horribly complex non-commented code. A wrong comment can lead someone completely in the wrong direction.? For that reason, a good developer always assumes comments are wrong.

A wrong comment can lead someone completely in the wrong direction.? For that reason, A comment almost always expresses an absolute thing, where a well named variable or method can express an abstract concept. Comments can actually tightly couple your code.? Take the example above where int i = 5 had a comment stating that 5 was the default.? DEFAULT_PRODUCTION_WIDGET_COUNT communicates the same information, but at a higher level of abstraction.

Comments can actually tightly couple your code.? Take the example above where int i = 5 had a comment stating that 5 was the default.? DEFAULT_PRODUCTION_WIDGET_COUNT communicates the same information, but at a higher level of abstraction. Comments don?t show up in stack traces. I have looked through many stack traces in my career, and I can tell you for a fact, that when you are looking at a stack trace, you would much prefer self-documenting method names, than good comments.

I have looked through many stack traces in my career, and I can tell you for a fact, that when you are looking at a stack trace, you would much prefer self-documenting method names, than good comments. Reading comments is optional. Reading code is mandatory.? You cannot count on anyone reading your comments.? You cannot force them to do so, but they must read the code. If you have something important to say, put it in the code.

NDoc and JavaDoc (XML style comments)

I am moving more and more away from even liking comments on public methods using JavaDoc or NDoc.? Most of the time when we create NDoc style documentation, we end up just restating exactly what the parameter name is.? How useful, really, is: cookieCount ? the count of cookies? Does that actually help someone using your code?? I would much rather make method names that have intuitive names and parameters than follow an arbitrary convention that adds no real value.

There is even a tool that auto creates NDoc comments for you.? Seriously, I used to think that was cool, but really how stupid is that?? Auto-generating comments?? Before you disagree with me here, really think about if embedding XML into your source code is really adding any value.

I understand creating MSDN style documentation is pretty cool.? I?ve used NDoc and SandCastle myself.? But, wouldn?t the effort be better spent creating more meaningful names and self-explanatory APIs?

Exceptions

Sometimes, you will need to write comments.? But, it should be the exception not the rule.? Comments should only be used when they are expressing something that cannot be expressed in code.? If you are using some mathematical equation, you might reference that equation in a comment, rather than trying to codifying it.

If you want to write elegant code, strive to eliminate comments and instead write self-documenting code.

Update: Just wanted to add this link to my original post on Elegant Code. And the link to my main personal blog at http://simpleprogrammer.com, since some people were getting confused.? Also, you can follow me on twitter here.