In Python a function is a value, like a number or a list. You can store one in a variable, pass one to another function, and even make one inside another function and hand it back.
Functions that make functions
def make_adder(n):
def add(x):
return x + n
return add
add_five = make_adder(5)
add_ten = make_adder(10)
print(add_five(1)) # 6
print(add_ten(1)) # 11make_adder builds a new function called add and returns it. When make_adder finishes, its variable n would normally be gone, but add still needs it, so Python keeps it attached to the returned function. A function that carries variables from the function that made it is a closure.Changing a remembered variable: nonlocal
Reading an outer variable just works. Assigning to it does not: inside
bump, count = count + 1 would make a new local count and fail. nonlocal count tells Python you mean the one in the enclosing function.def make_counter():
count = 0
def bump():
nonlocal count
count += 1
return count
return bump
tally = make_counter()
tally()
tally()
print(tally()) # 3Compare it with
global from the previous lesson: global reaches the module's top level, while nonlocal reaches into the functions this one was made inside, nearest first.How Python finds a name: LEGB
When your code uses a name, Python looks in four places, in this order, and takes the first one it finds:
- Local: the current function.
- Enclosing: any function the current one was made inside.
- Global: the top level of the module.
- Built-in: names Python always has, such as
lenandprint.