Writing Clean Code and Comments
Learn to write clean Python code: clear variable names, helpful comments and docstrings, avoiding repetition with functions, consistent spacing, and removing magic numbers. With runnable code and a quiz.
Key takeaways
- Clear, descriptive names make code readable without needing extra explanation
- Comments explain WHY code does something, not what each obvious line does
- A docstring describes what a function does, written just under the def line
- Don't Repeat Yourself: turn repeated code into a function you call
- Replace mystery 'magic numbers' with named constants that explain their meaning
Code is read more than it is written
When you write a program, it's easy to focus only on getting it to work. But code has a second, equally important job: being read and understood — by your teammates, your teacher, and especially by future you, who will have forgotten exactly how it worked. Clean code is code that communicates clearly. It runs the same as messy code, but it's far easier to fix, change and build on.
This lesson collects habits that make Python pleasant to read. None of them are hard, and together they separate a beginner's tangle from a program that looks professional. They build on everything from variables to functions.
Choose clear names
The single biggest improvement you can make is naming things well. Compare these two snippets that do the same thing:
# Unclear
x = 5
y = 12
z = x * y
print(z)
# Clear
rows = 5
seats_per_row = 12
total_seats = rows * seats_per_row
print(total_seats)
- The first version "works", but
x,yandztell you nothing. You'd have to trace the maths to guess what's going on. - The second version reads almost like English: rows times seats per row gives total seats. No comment needed — the names are the explanation.
Good Python names are lowercase with underscores between words (total_seats, not totalSeats or ts), and they describe what the value means, not its type.
Comments explain WHY, not WHAT
A comment is a note for humans that Python ignores. It starts with #:
# This is a comment. Python skips it entirely.
score = 0 # a comment can also sit at the end of a line
The common beginner mistake is commenting the obvious:
count = count + 1 # add 1 to count <- pointless, the code already says this
That comment just repeats the code. A useful comment explains the reason — the bit the code can't show:
# Skip the header row, which doesn't contain real data
start = 1
Here the why ("the header row isn't real data") is genuinely helpful, because you couldn't guess it from start = 1 alone. Rule of thumb: if good names make a line obvious, it needs no comment. Save comments for decisions and tricky logic.
Document functions with docstrings
When you write a function, a docstring describes what it does. It's a triple-quoted string placed right under the def line:
def celsius_to_fahrenheit(celsius):
"""Convert a temperature in Celsius to Fahrenheit."""
return celsius * 9 / 5 + 32
print(celsius_to_fahrenheit(100)) # 212.0
- The
"""..."""line is the docstring. It explains the function's purpose in one clear sentence. - Anyone using your function can read the docstring to understand it without studying the code inside.
Docstrings are special: tools and editors can display them automatically, and you can read one with help(celsius_to_fahrenheit). They're the professional way to document what a function does.
Don't Repeat Yourself (DRY)
If you find yourself copying and pasting the same lines, that's a signal to use a function. This idea is so important it has a name: DRY — Don't Repeat Yourself.
# Repetitive
print("Hello, Sam! Welcome aboard.")
print("Hello, Ada! Welcome aboard.")
print("Hello, Lee! Welcome aboard.")
# DRY: write it once, call it many times
def greet(name):
"""Print a friendly welcome message for one person."""
print(f"Hello, {name}! Welcome aboard.")
greet("Sam")
greet("Ada")
greet("Lee")
- The repetitive version copies the same sentence three times. If you want to change the wording, you must edit it in three places — and you might miss one.
- The DRY version has the sentence in one place. Change it once and every call updates. There's less to read, less to type, and far less chance of an inconsistent mistake.
Banish magic numbers
A magic number is a bare number in your code whose meaning isn't obvious:
price = 50
final = price * 0.2 + price # what is 0.2??
What does 0.2 mean? You can only guess. Give it a name — a named constant — and the mystery vanishes:
TAX_RATE = 0.2 # 20% sales tax
price = 50
final = price + price * TAX_RATE
print(final) # 60.0
TAX_RATE = 0.2names the value, so the calculation now reads clearly.- Constants are written in
UPPERCASEby convention, signalling "this value shouldn't change." - Bonus: if the tax rate ever changes to 0.25, you edit one line instead of hunting for every
0.2in your program.
Consistent spacing and structure
Python is strict about indentation, but clean code goes further with consistent, calm spacing:
# Cramped
total=0
for n in [1,2,3]:total=total+n
# Clean
total = 0
for n in [1, 2, 3]:
total = total + n
- Put a single space around operators (
total = 0, nottotal=0) and after commas in a list. - Give each statement its own line; don't cram the loop body onto the
forline.
These small touches make code breathe, so the eye can scan it easily.
Worked example: cleaning up a messy program
Here's a working but messy program, then a cleaned-up version that does exactly the same thing.
# Messy version
a=20
b=4
c=a*b
print(c)
d=a*b*0.2
print(d)
# Clean version
DISCOUNT_RATE = 0.2 # 20% loyalty discount
item_price = 20
quantity = 4
subtotal = item_price * quantity
discount = subtotal * DISCOUNT_RATE
print("Subtotal:", subtotal) # Subtotal: 80
print("Discount:", discount) # Discount: 16.0
What changed, and why it's better:
- Names:
a,b,cbecameitem_price,quantity,subtotal. The code now explains itself. - No magic number:
0.2became the named constantDISCOUNT_RATE, with a comment giving its meaning. - Spacing and labels: spaces around
=and, and the prints now say what* they're showing.
Both programs compute the same numbers, but only one of them you'd happily hand to a teammate.
Try it yourself
Take this deliberately messy snippet and clean it up:
x=8
y=6
z=x*y/2
print(z)
(It calculates the area of a triangle with base 8 and height 6.)
- Rename the variables to
base,heightandarea. - Replace the magic
2with a named constant or an explanatory comment. - Wrap it in a function called
triangle_area(base, height)with a docstring, so you can reuse it. - Add a labelled print like
print("Area:", area).
Then call your function with a couple of different sizes. Once your code reads cleanly, revisit an older program of yours and tidy it the same way. For more on bundling reusable logic, see functions and parameters.
Quick quiz
Test yourself and earn XP
Which variable name is the cleanest?
total_score describes exactly what it holds, so anyone reading the code understands it instantly.
What should a good comment usually explain?
The code already shows WHAT it does. A good comment adds WHY, the reason that isn't obvious from the code.
What is a docstring?
A docstring is a triple-quoted text just under the def line that describes what the function does.
What does the DRY principle stand for?
DRY means Don't Repeat Yourself: write logic once and reuse it instead of copying and pasting.
Why replace a 'magic number' with a named constant?
A name like TAX_RATE explains what 0.2 means, and if it ever changes you update it in just one spot.
FAQ
Usually not in any noticeable way — the computer runs messy and tidy code at almost the same speed. The real benefit of clean code is for humans. Clear names, helpful comments and no repetition make a program far easier to read, fix and extend, including for you in a few weeks when you've forgotten the details. Programmers spend much more time reading code than writing it, so readability is one of the most valuable skills you can build.
Yes. A comment on every single line, especially one that just restates the obvious like '# add 1 to count' above count = count + 1, becomes clutter that you have to read past. Worse, comments can go out of date when the code changes, leaving a misleading note. The aim is well-named code that mostly explains itself, with comments saved for the WHY and for anything genuinely tricky.
Keep exploring
More in Coding