How to remove an indentation error in Python
Struggling with Python indentation errors? Learn how to fix them with our guide, covering tips, real-world examples, and debugging methods.

Python uses indentation to define code blocks, a unique feature that often causes IndentationError. These common errors can stop a program, but they are simple to fix with practice.
Here, you will find techniques to identify and correct these errors. You'll get practical tips, see real-world examples, and receive debugging advice to help you write clean, error-free Python code.
Basic indentation rules in Python
def greet(name):
if name:
print(f"Hello, {name}!")
else:
print("Hello, world!")
greet("Python")--OUTPUT--Hello, Python!
In the greet function, indentation dictates the code's structure. It's how Python groups statements into blocks. Notice the different levels of indentation at play:
- The
if/elseblock is indented once, which places it inside thegreetfunction's scope. - The
print()statements are indented again, nesting them within their respective conditional blocks.
This strict, visual hierarchy is mandatory in Python. It replaces the curly braces common in other languages and is fundamental to how the interpreter understands your program's logic. A mistake here is a syntax issue, not a style preference.
Tools and techniques for preventing indentation errors
Following these strict rules becomes second nature when you adopt a few key practices and leverage modern development tools.
Using consistent spaces instead of tabs
def calculate_sum(numbers):
total = 0
for number in numbers:
total += number
return total
print(calculate_sum([1, 2, 3, 4]))--OUTPUT--10
In the calculate_sum function, each level of indentation uses four spaces. This consistency is key to avoiding errors. While tabs might look the same as spaces in your editor, Python sees them as different, which often leads to a frustrating IndentationError.
- Stick to one method—preferably spaces. The official PEP 8 style guide recommends four spaces per indent level.
- Most code editors can be set to automatically convert tabs to spaces, making this an easy habit to adopt.
Enabling indentation guides in your editor
def process_data(data):
results = []
for item in data:
# Most editors show visual guides for indentation
processed = item * 2
results.append(processed)
return results
print(process_data([5, 10, 15]))--OUTPUT--[10, 20, 30]
Most code editors offer indentation guides—faint vertical lines that align with your code blocks. In the process_data function, these guides would visually confirm that both processed = item * 2 and results.append(processed) are correctly nested within the for loop. This makes the code's structure obvious at a glance.
- These visual cues help you instantly spot misaligned lines, a common source of
IndentationError.
Activating this feature in your editor’s settings is a simple step that prevents many debugging headaches, especially in more complex, nested logic.
Using automatic code formatters like black
# Before running black:
def messy_function():
x = 10 # inconsistent indentation
if x > 5:
print("This would be fixed") # too many spaces
return x
# After black: consistent 4-space indentation everywhere--OUTPUT--def messy_function():
x = 10
if x > 5:
print("This would be fixed")
return x
Tools like black are automatic code formatters. They take the guesswork out of styling by rewriting your code to follow a strict, consistent standard. This means you don't have to manually fix indentation—the tool does it for you, as seen in the messy_function example.
- It enforces a single style guide across your project, which resolves inconsistent spacing and prevents potential
IndentationErrorissues. - Integrating a formatter into your workflow ensures your code remains clean and functional without extra effort.
Advanced indentation management
Beyond basic formatting, you can manage complex structures with advanced techniques, including the textwrap and contextlib modules for cleaner, more readable code.
Working with multi-level and continued indentation
def complex_example(value):
if (value > 10 and
value < 20): # continuation line indented
for i in range(2):
if i > 0: # nested blocks
print(f"Value: {value}, i: {i}")
complex_example(15)--OUTPUT--Value: 15, i: 1
In the complex_example function, indentation clearly defines the nested logic. The for loop sits inside the first if block, and the second if statement is nested even deeper. This visual structure is how Python understands the program's flow, especially in complex functions.
- When a statement is too long for one line, like the
if (value > 10 and value < 20)condition, you can break it up. The continued line is indented to show it's part of the same expression. - Each nested block requires its own level of indentation, which visually separates its scope from the surrounding code.
Using the textwrap module to fix string indentation
import textwrap
code = textwrap.dedent("""
def example():
print("This removes leading whitespace")
if True:
print("While preserving relative indentation")
""").strip()
print(code)--OUTPUT--def example():
print("This removes leading whitespace")
if True:
print("While preserving relative indentation")
The textwrap module is a powerful tool for managing strings that contain code. When you define a multi-line string within your program, it often picks up unwanted indentation from its surroundings. The textwrap.dedent() function intelligently removes this common leading whitespace from every line.
- It preserves the string's internal structure, so the relative indentation of your code block remains intact.
- The final
.strip()call is used to remove any blank lines from the beginning or end of the string.
This makes it perfect for cleaning up code templates or dynamically generated scripts without messing up their formatting.
Using contextlib to reduce indentation depth
from contextlib import contextmanager
@contextmanager
def indented_section():
try:
yield
finally:
print("Section complete")
with indented_section():
print("This reduces excessive nesting")--OUTPUT--This reduces excessive nesting
Section complete
The contextlib module offers a clever way to manage resources and reduce nested code. By using the @contextmanager decorator, you can create functions that handle setup and teardown logic automatically when used with a with statement. This pattern helps you avoid deep try...finally blocks, which keeps your code flatter and more readable.
- In the example,
indented_sectiondefines a context. The code inside thewithblock runs where theyieldkeyword is. - The
finallyblock executes automatically after thewithblock completes, encapsulating the cleanup logic without extra indentation.
Move faster with Replit
Replit is an AI-powered development platform that lets you start coding Python instantly. It comes with all Python dependencies pre-installed, so you can skip the setup and get straight to building.
Instead of just fixing indentation, you can build complete applications. With Agent 4, you move from learning individual techniques to shipping a finished product. For example, you could describe tools that use the functions from this article:
- A code formatter that uses
textwrap.dedent()to automatically clean up and standardize Python scripts. - A configuration validator that reads indented text files and confirms that all nested settings follow a predefined structure.
- A temporary file utility that uses
contextlibto create, write to, and automatically delete files within a single operation.
Simply describe your app, and Replit will write the code, test it, and fix issues automatically, all within your browser.
Common errors and challenges
Even with good practices, common indentation errors can appear, but they're simple to fix once you know what they mean.
Fixing IndentationError: unexpected indent errors
The IndentationError: unexpected indent pops up when a line has too much indentation for no reason. Python gets confused, thinking you're starting a new block where one doesn't belong. Check out the code below for a clear example.
def calculate_average(numbers):
total = sum(numbers)
count = len(numbers)
average = total / count # This line has too much indentation
return average
print(calculate_average([1, 2, 3, 4, 5]))
Inside calculate_average, the line average = total / count is indented without starting a new logical block. Python expects lines at the same level to have the same indentation, which is what causes the error. Here’s how to fix it.
def calculate_average(numbers):
total = sum(numbers)
count = len(numbers)
average = total / count
return average
print(calculate_average([1, 2, 3, 4, 5]))
The fix is straightforward. By realigning average = total / count with the other statements in the calculate_average function, the error is resolved. This issue happens when a line is indented without belonging to a new code block, like a loop or an if statement. It’s a common problem when copying and pasting code, so always double-check your alignment to ensure every line sits at its correct level within the function's scope.
Solving IndentationError: unindent does not match any outer indentation level
This error happens when a line's indentation doesn't align with any previous block. It's as if a line of code has gone rogue, breaking the visual structure Python relies on. The code below shows how this misalignment confuses the interpreter.
def process_items(items):
results = []
for item in items:
if item > 10:
print(f"Processing {item}")
result = item * 2
results.append(result)
return results
process_items([5, 15, 25])
Inside the if block, the lines beginning with result = item * 2 and results.append(result) are out of sync. Their indentation doesn't match any previous level, which breaks the logical flow. The corrected alignment is shown below.
def process_items(items):
results = []
for item in items:
if item > 10:
print(f"Processing {item}")
result = item * 2
results.append(result)
return results
process_items([5, 15, 25])
The fix aligns result = item * 2 and results.append(result) with the print statement, ensuring all lines inside the if block share the same indentation. This restores the logical structure Python expects.
- This error often appears when refactoring code or accidentally mixing spaces and tabs.
- Keep an eye on alignment to ensure all statements within a single block are perfectly synced.
Debugging mixed tabs and spaces in indentation
Mixing tabs and spaces is a classic Python pitfall because they look identical but are treated differently by the interpreter. This invisible difference creates an IndentationError that can be tricky to spot, as the code might appear perfectly aligned.
The code below shows this issue in action inside the analyze_data function, where a single tab disrupts the expected indentation.
def analyze_data(data):
results = []
for value in data:
if value > 0: # This line uses a tab instead of spaces
results.append(value * 2)
else:
results.append(0)
return results
print(analyze_data([-1, 2, 3, -4]))
In the analyze_data function, the tab before if value > 0: creates an indentation level that doesn't match the surrounding code. Python rejects this inconsistency. The corrected version below shows how to fix the alignment.
def analyze_data(data):
results = []
for value in data:
if value > 0: # Consistent spaces instead of tabs
results.append(value * 2)
else:
results.append(0)
return results
print(analyze_data([-1, 2, 3, -4]))
The fix replaces the tab before if value > 0: with spaces, aligning it correctly inside the for loop. This ensures every line in the block uses consistent spacing, which resolves the error. This issue often happens when you copy and paste code from different sources.
- To prevent it, configure your editor to automatically convert tabs to spaces. This simple setting saves a lot of debugging time by enforcing a consistent style.
Real-world applications
Mastering indentation isn't just about fixing errors; it's essential for working with data formats like YAML and building tools that generate code.
Parsing indentation-based data formats like YAML
Since formats like YAML also use indentation to define structure, your Python experience makes parsing them straightforward.
import yaml
yaml_data = """
person:
name: Alice
skills:
- Python
- Data Analysis
"""
parsed_data = yaml.safe_load(yaml_data)
print(parsed_data['person']['skills'])
This code shows how to parse a YAML string into a native Python object. The yaml.safe_load() function takes the yaml_data string and converts its structure into a Python dictionary. This makes it easy to work with the data programmatically.
- The
YAMLformat is often used for configuration files because it's human-readable. - Once parsed, you can access nested values using familiar dictionary keys and list indices, as shown with
parsed_data['person']['skills'].
Building code generators with proper indentation
When you build tools that generate code, you're responsible for programmatically adding the correct indentation to ensure the output is valid Python.
def generate_python_class(class_name, methods):
code = f"class {class_name}:\n"
if not methods:
code += " pass\n"
else:
for method in methods:
code += f" def {method}(self):\n"
code += f" return '{method} called'\n"
return code
print(generate_python_class("MyClass", ["start", "stop"]))
The generate_python_class function builds a complete Python class definition as a single string. It's a practical example of code generation, where you write code that writes other code. The function uses f-strings to piece together the class structure dynamically.
- It starts with the basic
classdeclaration and then loops through a list of method names. - For each name, it constructs a full method definition, including the
defline and a simplereturnstatement. - If the list of methods is empty, it adds a
passstatement to create a valid, empty class.
Get started with Replit
Put these concepts into practice and build a real tool. Describe what you want to Replit Agent, like “a Python utility that cleans up indentation in code snippets” or “a web tool that validates YAML files.”
Replit Agent writes the code, tests for errors, and helps you deploy your application. Start building with Replit and turn your idea into a working app.
Describe what you want to build, and Replit Agent writes the code, handles the infrastructure, and ships it live. Go from idea to real product, all in your browser.
Create & deploy websites, automations, internal tools, data pipelines and more in any programming language without setup, downloads or extra tools. All in a single cloud workspace with AI built in.

.png)
.png)
.png)