The essentials

Quick reference

One focused task per row. Jump to the related section for complete, working examples.

UseSyntaxExamples
Return a closurereturn innerView examples
Rebind enclosing statenonlocal countView examples
Inspect captured valuesvalues = function.__closure__View examples
Apply a decorator@decoratorView examples
Preserve wrapper metadata@wraps(function)View examples
Reach the wrapped callableoriginal = decorated.__wrapped__View examples
Configure a decorator@repeat(times=3)View examples
Stack decoratorsresult = outer(inner(function))View examples
Make instances callabledef __call__(self, value): return self.prefix + valueView examples
Check callabilitysupported = callable(value)View examples
Bind selected argumentsconfigured = partial(function, fixed_arg, option=value)View examples
Bind arguments on methodsmethod = partialmethod(function, fixed_arg)View examples
Register a type implementation@render.register(str)View examples
Inspect dispatch resolutionimplementation = render.dispatch(value_type)View examples
Memoize bounded results@lru_cache(maxsize=128)View examples
Clear a function cachefunction.cache_clear()View examples
Inspect cache statisticsstats = function.cache_info()View examples

Python treats functions, bound methods, classes, and objects implementing __call__ as values that can be stored and composed. Closures retain lexical state, decorators replace a definition with a transformed callable, and functools supplies standard adapters. Preserve introspection, make state ownership obvious, and resist wrappers that quietly change the original calling contract.

Step by step

Detailed examples

01

Capture lexical state deliberately

A closure is a nested function that refers to bindings from an enclosing function after that call has returned. Reading needs no declaration; rebinding requires nonlocal, which targets the nearest enclosing function scope rather than global state. Separate closure instances own separate captured bindings, making closures useful for small configured functions while a class may better express extensive mutable state.

Create independent stateful counters
def make_counter(start=0):
    count = start
    def increment(step=1):
        nonlocal count
        count += step
        return count
    return increment

first = make_counter(10)
second = make_counter()
print(first(), first(5))
print(second(), second())
print(first.__closure__[0].cell_contents)
Output
11 16
1 2
16
Back to quick reference ↑
02

Preserve metadata when wrapping a function

A decorator expression is evaluated when the def statement executes, and its result replaces the defined name. A general wrapper normally accepts *args and **kwargs and returns the original result. functools.wraps copies metadata such as __name__ and __doc__ and exposes __wrapped__, supporting inspection, documentation tools, testing, and further decorator composition.

Trace calls without hiding identity
from functools import wraps

def traced(function):
    @wraps(function)
    def wrapper(*args, **kwargs):
        print(f'calling {function.__name__}')
        return function(*args, **kwargs)
    return wrapper

@traced
def add(left, right):
    """Add two values."""
    return left + right

print(add(2, 3))
print(add.__name__, add.__doc__)
print(add.__wrapped__(4, 5))
Output
calling add
5
add Add two values.
9
Back to quick reference ↑
03

Configure wrappers with decorator factories

A decorator with arguments adds a factory layer: the expression first produces a decorator, which then receives the function. With stacked decorators, the decorator closest to def is applied first, although calls enter the outermost wrapper first. Validate configuration in the factory so errors appear at definition or import time rather than on a later call.

Repeat a call with validated configuration
from functools import wraps

def repeat(times):
    if times < 1:
        raise ValueError('times must be positive')
    def decorate(function):
        @wraps(function)
        def wrapper(*args, **kwargs):
            return [function(*args, **kwargs) for _ in range(times)]
        return wrapper
    return decorate

@repeat(times=3)
def label(value):
    return f'item-{value}'

print(label(7))
Output
['item-7', 'item-7', 'item-7']
Back to quick reference ↑
04

Use callable objects when behavior needs explicit state

An instance whose class defines __call__ participates in ordinary call syntax. This keeps configuration and mutable state inspectable as attributes and can be clearer than a deep closure. callable checks whether an object supports calling but cannot prove a particular argument list will succeed; use an explicit protocol or signature inspection when the contract matters.

Track transformations in a callable instance
class Prefixer:
    def __init__(self, prefix):
        self.prefix = prefix
        self.calls = 0

    def __call__(self, value):
        self.calls += 1
        return f'{self.prefix}{value}'

label = Prefixer('ID-')
print(callable(label))
print(label(3), label(8))
print(label.calls)
Output
True
ID-3 ID-8
2
Back to quick reference ↑
05

Pre-bind arguments with partial

functools.partial returns a callable that prepends positional arguments and supplies default keywords while still allowing ordinary call-time arguments. It is useful for adapters passed to APIs expecting a simpler callback. partialmethod provides descriptor-aware binding inside classes. Prefer a named wrapper when the adaptation needs validation, documentation, or nontrivial control flow.

Configure reusable base conversions
from functools import partial

base2 = partial(int, base=2)
base16 = partial(int, base=16)
print(base2('101101'))
print(base16('ff'))

def label(prefix, value, *, suffix=''):
    return f'{prefix}{value}{suffix}'

error = partial(label, 'E-', suffix='!')
print(error(404))
Output
45
255
E-404!
Back to quick reference ↑
06

Dispatch on the first argument's type

singledispatch turns a function into a generic function selected from the runtime type of its first argument. Registered implementations follow the class MRO and abstract base class registrations, while the undecorated base function is the fallback. It is an extension mechanism, not multiple dispatch: other argument types do not influence selection.

Render values with registered implementations
from functools import singledispatch

@singledispatch
def render(value):
    return f'object:{value}'

@render.register
def _(value: list):
    return '[' + ','.join(map(str, value)) + ']'

@render.register(str)
def _(value):
    return value.upper()

print(render(7))
print(render(['a', 2]))
print(render('ready'))
print(render.dispatch(bool) is render.dispatch(int))
Output
object:7
[a,2]
READY
True
Back to quick reference ↑
07

Cache pure, hashable calls with bounded storage

lru_cache stores return values by argument key, so arguments must be hashable and callers with equivalent but differently arranged keyword arguments may occupy separate entries. Caching is appropriate when results depend only on arguments and remain valid. Bound methods include self in the key, and cached references stay alive until eviction or cache_clear, so choose maxsize with memory and freshness in mind.

Observe cache hits and reset state
from functools import lru_cache

@lru_cache(maxsize=2)
def square(value):
    print(f'compute {value}')
    return value * value

print(square(4))
print(square(4))
print(square.cache_info().hits, square.cache_info().misses)
square.cache_clear()
print(square.cache_info().currsize)
Output
compute 4
16
16
1 1
0
Back to quick reference ↑

Local code tester

Compose a stateful decorated callable

Configure a closure, preserve its metadata, and inspect memoization behavior while editing the call sequence.

Runs in your browser
Output
Press Run to load Python locally.

Sources and further reading

References

Authoritative documentation used to verify and expand this cheat sheet.

  1. Python Software FoundationFunction definitions and decoratorsdocs.python.org
  2. Python Software Foundationfunctools — Higher-order functions and operations on callable objectsdocs.python.org
  3. Python Software FoundationNaming and bindingdocs.python.org
  4. Python Software FoundationPEP 318 – Decorators for Functions and Methodspeps.python.org

Help us improve

Found a typo or missing example?

Tell us what would make this cheat sheet clearer, more complete, or more useful.

Share feedback