Python PEP8 Guidelines
Introduction
When you're learning Python, it's not just about writing code that works—it's also about writing code that's clean, readable, and maintainable. That's where PEP8 comes in.
PEP8, or Python Enhancement Proposal 8, is Python's official style guide. It provides a set of conventions for writing Python code that makes it more consistent and easier to read. Following these guidelines is a best practice that will help you become a better Python programmer and collaborate more effectively with others.
In this guide, we'll explore the key elements of PEP8 and learn how to apply them to our Python code.
What is PEP8?
PEP stands for "Python Enhancement Proposal," and PEP8 specifically deals with the style guide for Python code. Created by Guido van Rossum (Python's creator), Barry Warsaw, and Nick Coghlan in 2001, PEP8 has become the standard style guide that most Python developers follow.
The guiding principle behind PEP8 is simple:
Code is read much more often than it is written.
This means that readability matters a lot, and following consistent style guidelines helps everyone understand your code better.
Key PEP8 Guidelines
1. Indentation
Python uses indentation to define code blocks. PEP8 recommends:
- Use 4 spaces per indentation level
- Never mix tabs and spaces
# Correct indentation (4 spaces)
def function():
if True:
print("Properly indented")
# Incorrect indentation (2 spaces)
def function():
if True:
print("Incorrectly indented")
2. Line Length
PEP8 recommends keeping lines at a maximum of 79 characters for code and 72 for comments and docstrings.
# Too long line
result = some_function_with_a_really_long_name(parameter1, parameter2, parameter3, parameter4, parameter5, parameter6, parameter7)
# Better - using line continuation with parentheses
result = some_function_with_a_really_long_name(
parameter1,
parameter2,
parameter3,
parameter4,
parameter5,
parameter6,
parameter7
)
3. Imports
PEP8 has specific guidelines for organizing imports:
- Imports should be at the top of the file
- Group imports in this order: standard library imports, related third-party imports, local application/library imports
- Put a blank line between each group
- Imports should be on separate lines
# Correct import grouping
import os
import sys
from datetime import datetime
import numpy as np
import pandas as pd
from myproject.models import User
from myproject.utils import helper_function
4. Whitespace
Proper whitespace usage improves readability:
Avoid Extraneous Whitespace
# Correct
spam(ham[1], {eggs: 2})
# Incorrect (extra whitespace)
spam( ham[ 1 ], { eggs: 2 } )
Use Whitespace Around Operators
# Correct
x = 1
y = 2
long_variable = 3
# Incorrect
x=1
y = 2
long_variable=3
Blank Lines
- Surround top-level functions and classes with two blank lines
- Method definitions inside a class are surrounded by a single blank line
# Correct use of blank lines
def top_level_function():
return None
class MyClass:
def method_one(self):
return None
def method_two(self):
return None
def another_function():
return None
5. Naming Conventions
PEP8 defines clear naming conventions:
snake_case
for variables, functions, methods, and modulesPascalCase
for class namesUPPER_CASE_WITH_UNDERSCORES
for constants- Use single leading underscore
_var
for internal use variables - Use double leading underscore
__var
for name mangling in classes
# Naming convention examples
# Constant
MAX_OVERFLOW = 100
# Function name
def calculate_total(price, tax):
return price * (1 + tax)
# Class name
class CustomerOrder:
# Method name
def process_payment(self):
# variable name
payment_status = "completed"
return payment_status
# Internal use method
def _validate_user(self):
pass
# Name mangled method (becomes _CustomerOrder__secret_method)
def __secret_method(self):
pass
6. Comments and Documentation
Well-documented code is essential:
- Use docstrings for modules, functions, classes, and methods
- Comments should be complete sentences and explain why, not what
- Keep comments up-to-date with code changes
# Module docstring example
"""
This module provides functions for processing financial data.
"""
def calculate_compound_interest(principal, rate, time):
"""
Calculate compound interest for given parameters.
Args:
principal: Initial investment amount
rate: Interest rate (decimal)
time: Time period in years
Returns:
float: The final amount after compound interest
"""
# Using the compound interest formula: A = P(1 + r)^t
return principal * (1 + rate) ** time
7. String Quotes
PEP8 doesn't enforce single or double quotes, but recommends consistency:
# Both are acceptable
name = "John"
address = 'New York'
# Use the other type of quotes to avoid escaping
message = "Don't forget to code"
query = 'SELECT * FROM "Users"'
Practical Example: Refactoring Code to PEP8
Let's look at a practical example of refactoring non-PEP8 compliant code:
Before (Non-PEP8 Compliant)
import random, sys, os
def get_user_score(userName,difficulty = "medium"):
"""Gets score for user"""
EASY_POINTS=10
MEDIUM_POINTS=20
HARD_POINTS=30
if(difficulty.lower()=="easy"): return EASY_POINTS
elif(difficulty.lower()=="medium"): return MEDIUM_POINTS
elif(difficulty.lower()=="hard"): return HARD_POINTS
else: return 0
class userScore :
def __init__ ( self,name ) :
self.name=name
self.score=0
def add_points(self,points):
self.score=self.score+points
After (PEP8 Compliant)
import os
import random
import sys
def get_user_score(user_name, difficulty="medium"):
"""
Calculate user score based on difficulty level.
Args:
user_name: Name of the user
difficulty: Game difficulty (easy, medium, hard)
Returns:
int: Points earned based on difficulty
"""
EASY_POINTS = 10
MEDIUM_POINTS = 20
HARD_POINTS = 30
difficulty = difficulty.lower()
if difficulty == "easy":
return EASY_POINTS
elif difficulty == "medium":
return MEDIUM_POINTS
elif difficulty == "hard":
return HARD_POINTS
else:
return 0
class UserScore:
def __init__(self, name):
self.name = name
self.score = 0
def add_points(self, points):
self.score += points
Notice the improvements:
- Proper import organization
- Consistent 4-space indentation
- Better naming conventions (
userName
->user_name
,userScore
->UserScore
) - Improved docstrings
- Proper spacing around operators and after commas
- Consistent line breaks
- Using
+=
operator for more concise code
Tools to Help Follow PEP8
Several tools can help ensure your code follows PEP8:
-
flake8: A tool that checks your code against PEP8 and finds potential bugs
bashpip install flake8
flake8 your_file.py -
black: An opinionated code formatter that automatically reformats your code
bashpip install black
black your_file.py -
pylint: A static code analyzer that can check for PEP8 compliance
bashpip install pylint
pylint your_file.py -
IDE integrations: Most modern Python IDEs like PyCharm, VS Code, and others have built-in PEP8 checking and auto-formatting.
When to Break PEP8 Rules
PEP8 itself acknowledges that guidelines shouldn't be followed blindly. As the document states:
A style guide is about consistency. Consistency with this style guide is important. Consistency within a project is more important. Consistency within one module or function is the most important.
Sometimes, breaking a guideline can make your code more readable or maintainable. Use your judgment, especially in these cases:
- When applying the guideline would decrease readability
- When maintaining consistency with surrounding code that breaks the guideline
- When code needs to remain compatible with older Python versions
Summary
PEP8 is more than just a set of arbitrary rules—it's a tool for writing cleaner, more readable Python code. By following these guidelines:
- Your code becomes more consistent and professional
- Other developers can read and understand your code more easily
- You'll catch certain logical errors earlier through better visual organization
- Your codebase becomes more maintainable over time
Remember that while PEP8 provides excellent guidance, the ultimate goal is readability and maintainability. Use these guidelines intelligently to improve your Python code quality.
Additional Resources
- Official PEP8 Documentation
- PEP8 Online Checker
- Book: "Clean Code: A Handbook of Agile Software Craftsmanship" by Robert C. Martin
Practice Exercises
-
Code Review Practice: Take a piece of your existing Python code and review it according to PEP8 guidelines. Make the necessary changes to make it compliant.
-
Tool Setup: Install and configure flake8 or black in your development environment. Run it on your project.
-
Collaborative Practice: Find an open-source Python project on GitHub and look at their code style. Does it follow PEP8? Can you identify any deviations and understand why they might have chosen to deviate?
-
PEP8 Challenge: Write a small Python function (e.g., a function that calculates prime numbers) with intentional PEP8 violations. Then have a peer identify and fix the violations.
Happy coding with clean, PEP8-compliant Python!
If you spot any mistakes on this website, please let me know at [email protected]. I’d greatly appreciate your feedback! :)