// No comments

S. G.
S. G.
Jan 1 · 4 min read

“Comments should account for 5% of the total points” my fellow teacher declared.

In the fall of 2019, I was co-teaching an introductory course in computer programming and got into a disagreement on whether the students should be required to incorporate comments into their project submission.

“I want the students to develop good practices early on in their career. Surely, you’ll agree that adding comments improves code quality?” the fellow teacher asked me, almost righteously, a little miffed at my pushback.

I disagreed, and emphatically. Being encouraged to sprinkle comments everywhere is probably the worst programming practice being taught in school. Barring certain cases where comments are justified (I cover that later), adding comments is an anti-pattern, and an excessively commented code-base suggests a need to refactor.

Wait, what is this heresy? Comments can’t possibly hurt. Can they?

Here are the two reasons why I consider comments to be an anti-pattern:

  1. They invariably go out of date. People forget to update comments as code gets refactored and features are developed. When this happens, comments become the root cause of the very thing they are meant to avoid — confusion. This is especially true at large companies where there are several people actively changing a common codebase. Imagine the plight of a poor new hire who just can’t wrap his head around why the house has an empathic comment calling it a Palm Tree.
  2. Programmers (myself included) write comments that are redundant or poor. I’ve observed this to be the case at every company I’ve worked at and many excellent programmers are guilty of this. On my team at Google, we had a rule that every single protocol buffer definition needed to be preceded by a comment. So we had way too many instances of code that looked like the following:
// Represents a Dog.
message Dog {
// The id of the dog.
string id = 0;
// The name of the dog.
string name = 1;
// The breed of the dog.
string breed = 2;
}

Redundant comments are noise, and can make files twice as long as they need to be.

Allrighty, I see your point. Redundant comments are dumb. But what about the instances where comments are needed to explain what my code is doing?

You can almost always find other ways to convey what your code is doing. A common strategy is to use well named temporary variables or method names to convey intention. Let’s look at a concrete example in code. I’m using python, since it’s most pseudo-code like, but the concept is programming language agnostic.

In this example, we are sending payouts to sellers when certain conditions are met. An example would be a seller on Amazon receiving lump sum payments for their sales on the platform:

# Seller is eligible to be paid under the following conditions:
# 1. It's past 2020/5/1 when we got legal approval to make payouts
# 2. It’s Nov/Dec since those are the only months eligible
# 3. User is not from list of countries that are banned
today = date.today()if today > date(2020, 1, 1) and (today.month == 11 or today.month == 12) and user.country not in ['Narnia', 'Odan', 'Maldonia']:
# This function does the actual payout by calling Stripe
# It saves the response asynchronously.
payoutHandler()

At first glance, it seems like comments are justified since they do enhance readability. Code is read many more times than it is written and so making code readable is a good thing. In this example, comments convey the following information:

  1. The conditions for making a payout. Without the comment at the start, the burden is on the reader to parse the verbose sub-conditions in the if statement to understand if the payout should happen.
  2. Why certain constants (2020/5/1, 11, 12 and [‘Narnia’, ‘Odan’, ‘Maldonia’]) are used and what they represent.
  3. What the payoutHandler() method will do.

Now let’s look at how this code can be re-written to convey the same information without using comments:

PAYOUT_APPROVAL_DATE = date(2020, 5, 1)
BANNED_COUNTRIES = ['Narnia', 'Odan', 'Maldonia']
NOVEMBER, DECEMBER = 11, 12
ELIGIBLE_MONTHS = [NOVEMBER, DECEMBER]
today = date.today()
is_past_approval_date = today > PAYOUT_APPROVAL_DATE
is_eligible_month = today.month in ELIGIBLE_MONTHS
is_user_from_banned_country = user.country in BANNED_COUNTRIES
if is_past_approval_date and is_eligible_month and not is_user_from_banned_country:
stripe_payout_resp = callStripeToPayout(user)
saveResponseAsync(stripe_payout_resp)

You’ll notice that the information that was being conveyed by comments is now being conveyed by using temporary variables (is_past_approval_date, is_eligible_month, is_user_from_banned_country), constants (BANNED_COUNTRIES) and verbs as function names.

Good naming is a powerful tool that can replace comments and help you write self-documenting code. Now this code can be refactored mercilessly without any fear of the house being mis-documented as a tree.

Ok, so is it really never cool to add comments? That sounds draconian.

Here’s my rule of thumb — don’t use comments to explain the what. Instead, use them to explain the why, and only when you can’t convey the why through naming. In most cases you can leverage on good naming to convey the why. For e.g. instead of adding this comment:

# This code removes the invalid control characters because the 
# AS400 processor cannot handle them

name your function

def remove_AS400_incompatible_control_chars():

If you can’t rely on naming to get the message across — for e.g. if your code is doing something subtle/non-obvious, then comments are definitely warranted. Here are some examples of useful comments:
# Prevents a rare but severe race condition which happens when...
# Closing this write transaction before making the RPC to prevent stale locks

It might be worth looking at your codebase to see if you can replace some of your existing comments with self-documenting code.

Follow me to be notified whenever I publish an article like this one. If you are are interested in interviewing, you might also want to check out my article called “The LeetCode Phenomenon”.

Credits: Icons in the comic strip made by Freepik from Flaticon

Sign up for Top 10 Stories

By The Startup

Get smarter at building your thing. Subscribe to receive The Startup's top 10 most read stories — delivered straight into your inbox, once a week. Take a look.

By signing up, you will create a Medium account if you don’t already have one. Review our Privacy Policy for more information about our privacy practices.

Check your inbox
Medium sent you an email at to complete your subscription.

S. G.

Written by

S. G.

I mostly write about programming, interviews and self improvement.

The Startup

Get smarter at building your thing. Follow to join The Startup’s +8 million monthly readers & +789K followers.

S. G.

Written by

S. G.

I mostly write about programming, interviews and self improvement.

The Startup

Get smarter at building your thing. Follow to join The Startup’s +8 million monthly readers & +789K followers.

Medium is an open platform where 170 million readers come to find insightful and dynamic thinking. Here, expert and undiscovered voices alike dive into the heart of any topic and bring new ideas to the surface. Learn more

Follow the writers, publications, and topics that matter to you, and you’ll see them on your homepage and in your inbox. Explore

If you have a story to tell, knowledge to share, or a perspective to offer — welcome home. It’s easy and free to post your thinking on any topic. Write on Medium

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store