Skip to main content

Naming Style and Readability

What You'll Learn​

Python's official naming conventions, how to write code that reads like prose, and when and how to document your code.

Why Readability Matters​

"Code is read far more often than it is written." — Guido van Rossum

You will spend more time reading code (yours and others') than writing it. Readable code:

  • Is easier to debug
  • Is easier for teammates to understand
  • Is less likely to have hidden bugs
  • Is easier to modify safely

PEP 8 — Python's Style Guide​

PEP 8 is the official Python style guide. Here are the most important rules:

Naming Conventions​

WhatConventionExample
Variablessnake_caseuser_name, total_count
Functionssnake_caseget_user(), calculate_total()
ConstantsUPPER_SNAKE_CASEMAX_RETRIES, BASE_URL
ClassesPascalCaseUserAccount, DatabaseError
Private (internal)_leading_underscore_internal_helper
Modules/fileslowercase or snake_caseutils.py, db_client.py
# ✅ Good
MAX_CONNECTIONS = 10
user_email = "[email protected]"

def calculate_average(numbers):
...

class UserProfile:
...

# ❌ Bad
maxConn = 10 # camelCase for variable
UserEmail = "alice" # PascalCase for variable
CalculateAverage() # PascalCase for function
userprofile = ... # lowercase for class

Descriptive Names​

# ❌ Cryptic
def calc(x, y, z):
return x * y + z

# ✅ Clear
def calculate_discounted_price(base_price, discount_rate, shipping_cost):
return base_price * (1 - discount_rate) + shipping_cost

Avoid single-letter names except for:

  • Loop counters: i, j, k
  • Math variables where it's conventional: x, y in geometry
  • Lambda one-liners: lambda x: x * 2

Whitespace and Spacing​

# Around operators
x = 5 + 3 # ✅
x=5+3 # ❌

# After commas
print(a, b, c) # ✅
print(a,b,c) # ❌

# Around = in keyword arguments (no spaces)
print(end="") # ✅
print(end = "") # ❌

# Blank lines
# 2 blank lines between top-level definitions
def first_function():
...


def second_function():
...

# 1 blank line between methods inside a class
class MyClass:
def first(self):
...

def second(self):
...

Line Length​

PEP 8 recommends 79 characters per line (many teams allow 99 or 120).

Break long lines using parentheses:

# Long function call — break inside parentheses
result = some_function(
argument_one,
argument_two,
argument_three,
)

# Long condition
if (
user.is_active
and user.has_permission("write")
and not user.is_banned
):
proceed()

# Long string
message = (
"This is a very long message that "
"spans multiple lines for readability."
)

Comments​

Good comments explain why, not what (the code shows what):

# ❌ Useless comment (restates the code)
x = x + 1 # increment x by 1

# ✅ Useful comment (explains the reason)
x = x + 1 # offset by 1 because array is 0-indexed but display is 1-indexed

# ❌ Wrong comment (misleading!)
y = x * 2 # double the price (actually doubles the count!)

# ✅ Correct and useful
item_count = raw_count * 2 # multiply by 2: each container holds 2 items

Block comments (above the code they describe):

# Retry up to 3 times with exponential backoff.
# The API has a rate limit of 100 requests/minute.
for attempt in range(3):
...

Inline comments (same line, at least 2 spaces):

timeout = 30 # seconds; API SLA requires response within 25s

Docstrings​

Docstrings document what a function does, its parameters, and return value:

def calculate_bmi(weight_kg: float, height_m: float) -> float:
"""
Calculate Body Mass Index (BMI).

Args:
weight_kg: Weight in kilograms.
height_m: Height in metres.

Returns:
BMI value as a float.

Raises:
ValueError: If height_m is zero or negative.
"""
if height_m <= 0:
raise ValueError(f"height_m must be positive, got {height_m}")
return weight_kg / (height_m ** 2)

Access docstrings with help():

help(calculate_bmi)

Type Hints​

Type hints make code self-documenting:

# Without type hints
def greet(name):
return "Hello, " + name

# With type hints — clearer what goes in and comes out
def greet(name: str) -> str:
return "Hello, " + name

# More complex types
from typing import Optional

def find_user(user_id: int) -> Optional[str]:
"""Returns username or None if not found."""
...

Auto-Formatting Tools​

Don't spend time manually formatting — use tools:

# black: opinionated auto-formatter
pip install black
black src/

# ruff: fast linter + formatter
pip install ruff
ruff check src/
ruff format src/

# isort: sorts import statements
pip install isort
isort src/

Quick Reference​

# Naming
variable_name = ... # snake_case
CONSTANT_NAME = ... # UPPER_SNAKE_CASE
def function_name(): ... # snake_case
class ClassName: ... # PascalCase

# Spacing
x = a + b # spaces around operators
func(a, b, c) # spaces after commas
func(key="value") # no spaces around = in kwargs

# Comments
# Explain why, not what

# Docstring
def fn(x: int) -> str:
"""Short description.

Args:
x: What x is.

Returns:
What the function returns.
"""

# Type hints
def fn(name: str, count: int = 1) -> list[str]:
...

What's Next​

→ Module 3: Data Structures