codingstuff.io
ExploreTutorialsProblemsCS Subjects
Get Started
ExploreTutorialsProblemsCS Subjects
Get Started
codingstuff.io

Master the art of building software through interactive tutorials, real-world problems, and guided projects.

Pune, Maharashtra, India

codingstuffmail@gmail.com

Product

  • Explore
  • Tutorials
  • Problems
  • CS Subjects

Company

  • About
  • Contact
  • Privacy Policy
  • Terms & Conditions
  • Sitemap

© 2026 codingstuff.io. All rights reserved.

Built with ❤️ for developers everywhere

/
/
All Tutorials
🐍

Python Programming

28 / 68 topics
24Python Functions25Function Arguments (*args, **kwargs)26Python Lambda Functions27Python Namespace & Scope (Global/Local)28Python Closures29Python Recursion
Tutorials/Python Programming/Python Closures
🐍Python Programming

Python Closures

Updated 2026-05-15
20 min read

Python Closures

In this tutorial, you'll learn about closures in Python. A closure is a function object that remembers values in enclosing scopes even if they are not present in memory. This concept builds on the understanding of namespaces and scope from the previous topic.

Closures are powerful tools in functional programming and can be used to create decorators, which we will explore later. Understanding closures will help you write more modular and reusable code.

What is a Closure?

A closure is created when a nested function references variables from its enclosing scope. The nested function retains access to these variables even after the outer function has finished executing. This is because the inner function "closes over" the environment in which it was created.

Real-World Analogy

Imagine you have a safe with a secret combination. The combination is known only by the person who opened the safe first. Even if that person leaves, anyone who follows them can still open the safe using the combination they learned. This is similar to how closures work: the inner function retains access to the variables of the outer function.

Creating Closures

To create a closure, you need to define a nested function inside another function and have the nested function refer to variables from the enclosing scope. Here's a simple example:

closure_example.py
1def outer_function(x):
2 def inner_function(y):
3 return x + y
4 return inner_function
5
6# Create a closure by calling the outer function
7closure = outer_function(10)
8
9# Use the closure
10result = closure(5)
11print(result) # Output: 15
Output
15

In this example, inner_function is a closure because it remembers the value of x from outer_function, even after outer_function has finished executing.

Capturing Variables

When a nested function captures variables from its enclosing scope, it captures the actual variables, not their values. This means that if the variables are mutable (like lists or dictionaries), changes to them will be reflected in the closure:

mutable_capture.py
1def outer_function():
2 count = [0]
3
4 def inner_function():
5 count[0] += 1
6 return count[0]
7
8 return inner_function
9
10counter = outer_function()
11print(counter()) # Output: 1
12print(counter()) # Output: 2
Output
1
2

In this example, count is a list that is captured by inner_function. Each call to counter() modifies the same list, demonstrating how closures can maintain state.

Practical Use Cases

Closures are particularly useful for creating functions with persistent state or for implementing decorators. Here's an example of using closures to create a simple counter:

counter.py
1def make_counter():
2 count = 0
3
4 def counter():
5 nonlocal count
6 count += 1
7 return count
8
9 return counter
10
11# Create two counters
12counter1 = make_counter()
13counter2 = make_counter()
14
15print(counter1()) # Output: 1
16print(counter1()) # Output: 2
17print(counter2()) # Output: 1
Output
1
2
1

In this example, counter1 and counter2 are independent closures that maintain their own state.

Closures vs. Decorators

Closures are closely related to decorators. A decorator is a higher-order function that takes another function and extends its behavior without explicitly modifying it. Closures can be used to implement decorators:

decorator_example.py
1def my_decorator(func):
2 def wrapper():
3 print("Something is happening before the function is called.")
4 func()
5 print("Something is happening after the function is called.")
6 return wrapper
7
8@my_decorator
9def say_hello():
10 print("Hello!")
11
12say_hello()
Output
Something is happening before the function is called.
Hello!
Something is happening after the function is called.

In this example, wrapper is a closure that captures the func variable from its enclosing scope. The decorator pattern uses closures to add functionality around existing functions.

Common Mistakes and Pitfalls

  1. Variable Scope Confusion: Ensure that variables captured by a closure are intended to be captured. Misunderstanding variable scopes can lead to bugs.
  2. Mutable Data Capture: Be cautious when capturing mutable data types, as changes to them will affect all closures that capture the same data.
  3. Memory Leaks: Closures can inadvertently hold onto large amounts of memory if they capture variables that are no longer needed.

Summary

  • A closure is a function object that remembers values in enclosing scopes.
  • Closures are created when a nested function references variables from its enclosing scope.
  • Closures can maintain state and are useful for creating decorators.
  • Be aware of common pitfalls related to variable scope and mutable data capture.

What's Next?

In the next tutorial, we will explore Python Recursion. Recursion is a powerful technique where a function calls itself to solve smaller instances of the same problem. Understanding recursion will help you write more efficient algorithms for tasks like searching and sorting.

Stay tuned!


PreviousPython Namespace & Scope (Global/Local)Next Python Recursion

Recommended Gear

Python Namespace & Scope (Global/Local)Python Recursion