BrainsToBytes

Writing good software comments II

In a previous article, we talked about the importance of comments in software development.

Even though they are powerful tools for improving the readability of our code, we should use them with care. A good comment can make the code easier to understand, but a bad one can harm your productivity.

Bad comments clutter your editor and make code harder to navigate and format. Extremely verbose comments are impossible to maintain and easily degrade after a couple of months. The most dangerous type, though, is the comment with false information: it misleads you and prevents you from making the right choices.

In this article, we will explore some of the most common forms of comments you should avoid.

Misleading comments

The code will change, it's a natural thing you can expect in every single software project.

Sometimes, the logic of your program will change in a way that makes a comment obsolete. It will lose context and become meaningless. If you find a comment that is obviously wrong you can safely remove it or update it.

Sometimes, the change will be more subtle, and it won't be obvious that the comment doesn't apply anymore. This type of comment is particularly dangerous because it leads you into assuming things that are not true anymore. If you base your implementation on this outdated information, the possibility of introducing new bugs in your code is dangerously high.

It's very hard to protect yourself against this problem. There are only two ways of guaranteeing this won't happen:

  • Not writing comments at all: Kind of a shame, as we know that some comments are genuinely useful.
  • Always updating comments to reflect the reality of our code: This would be ideal, but in practice is unlikely to happen unless you are the only person working on the project.

The solution is to comment only the things that matter, and if one of our remaining comment becomes invalid, update it immediately.

Logbook comments

Keeping a log at the top of each file used to be a popular way of keeping track of changes. Thankfully, now we have version control systems that take care of this in a much more efficient and clean way. If your code is not under version control yet and you still keep logs in each file, give any VCS a try, it's totally worth it.

// JUN 7 2007: Added new feature: Dogs can bark in 3 different languages
// FEB 20 2007: Added cat support, now our dogs can even be cats!
// FEB 7 2007: Went out with Robert for lunch, I wonder if he likes me ...
// JAN 22 2007: Added multithread support, this is a really efficient dog now
// JAN 13 2007: Added cool attributes 
// JAN 8 2007: Created initial version of this class
public class Dog{
    // Class implementation
}

Captain obvious comments

This type of article doesn't add any important information, it's just there to clutter your screen.

If your workplace has a policy of 'minimum number of comments per class', I'm willing to bet that like 90% of the comments you write belong in this category.

This is the type of comment you write just because, well, you need to comment your code, don't you?

Trimming the bloat and removing distractors is an important skill in our profession. Do your team a favor and remove comments that just state the obvious.

public class Dog{
    private String name;

    // Default constructor--OBVIOUS
    public Dog() {
        //Sets a default name - OBVIOUS
        name = "Laika";
    }

    // Other constructor that sets the name during construction - OBVIOUS
    public Dog(String dogName){
        name = dogName;
    }

    // getter for the name attribute - OBVIOUS
    public String getName(String dogName){
        name = dogName;
    }
}

In the code example above, you can remove every single comment. Instead of making the class harder to understand, this will make it much easier to read. Bad comments are a distraction. Remove distractors that only state the obvious and provide no valuable information.

One-line attribute redundancy

Have you ever seen a class like this?:

public class Dog {
    // The age of the dog
    private int ageInYears;
    // The weight of the dog
    private int weight;
    // The dog's name
    private String name;
    // The dog's breed
    private String breed;

    // Class implementation
}

Those comments are useless, they don't add any important information. What's more, the names of the attributes already give me more information than those comments: ageInYears even tells me the unit!

The only comment I would add would be a clarification that the dog's weight (it's actually mass, but you understand) is in kilograms or pounds. But something even better would be changing the variable name to massInKg or massInPounds.

This type of comment in the attribute section of a class is quite common, especially among beginner developers. Stop writing them and instead work in giving every variable a great name.

Using comments as bracket markers

This is something I used to do a lot.

When writing code we sometimes find nested structures within loops and conditionals. Knowing which brackets belong together is a bit hard if the structure is complex enough, the solution? Write comments next to the closing bracket to mark it.

This is useless now that we have text editors and IDEs that highlights the two brackets that belong together. Another reason not to use them is that, if your nested code is that complex, you might actually benefit from re-writing the code and create functions for the sub-operations. Instead of this:

for(...){
    //....
    //....
    //....
    if(...){
        //...
        //...
        for(...){
            //...
            //...
            //...
            //...
        }//inner for
        //...
        //...
    }//big if
    else{
        //...
        //...
        if(...){
        //...
        //...
        //...
        //...
        }//small if
        else{
        //...
        //...
        //...
        //...
        }//small else
        //...
        //...
    }// big else
}// outer for

You might want to write something like this:

for(...){
    function1();
    if(...){
        function2()
    }else{
        function3()
    }
}

function1(){...}
function2(){...}
function3(){...}

Or, depending on the case, decompose that structure even further.

Commenting out the code to disable it

This is an extremely common practice: instead of removing code altogether, just disable it with a comment.

This happens because we think that someday this code will be useful again. Or because (god forbid) commenting and uncommenting code for different deployments is the way we handle different systems.

If the code shouldn't be there, remove it. It's a liberating experience to clean your software from all those dead lines. Because most of our projects have a form of version control, you don't have to be afraid of losing that code. Go and trim the bloat, your project will feel much cleaner after it.

API documentation for private methods

Documenting the public interface of your classes with special documentation format is quite useful. You can use tools like Javadoc or YARD to automatically generate useful documentation about how to use your classes.

Private methods are a different matter: the user of your library doesn't care (and shouldn't) know the implementation details of your class. Information hiding is an extremely powerful feature that frees your brain from the info it doesn't need. Writing public documentation for these methods is a form of information hiding violation.

So, keep the public interface documentation for public methods, those are the ones users care about.

Writing good comments is hard

Writing comments is a similar skill to writing good variable names. The principles are very similar too: you want to communicate relevant information without cluttering your files. A good comment is both concise and informative, just like a good variable name.

Go and practice writing comments, and also practice removing them. Refactor your code to make it obvious to the reader: choose good variable names, write well-defined small functions, use obvious control structures. If you make your code's quality a priority, you will need much fewer comments and your colleagues will be happier to work with you.

Use comments wisely and try to make every single one of them count.

What to do next:

  • Share this article with friends and colleagues. Thank you for helping me reach people who might find this information useful.
  • You can find more information about creating good function arguments in chapter 4 of Clean Code, and in chapter 32 of Code Complete. This and other very helpful books can be found in the recommended reading list.
  • Send me an email with questions, comments or suggestions (it's in the About Me page). Come on, don't be shy!if
Author image
Budapest, Hungary
Hey there, I'm Juan. A programmer currently living in Budapest. I believe in well-engineered solutions, clean code and sharing knowledge. Thanks for reading, I hope you find my articles useful!