Take away from complex concepts , stay Python in , A closure is when you call a function X, This function returns one Y Function for you , This returned function Y It's a closure .
Before mastering any technology , We should first look at the most basic case code :
def func(parmas): # Internal function def inner_func(p): print(f" External function parameters {parmas}, Internal function parameters {p}") return inner_func inner = func(" Outside ") inner(" Inside ")
The description of the above code is as follows , Calling func(" Outside ")
A closure is generated when inner_func
function , The closure function calls an external function func
Parameters of parmas
, At this time parmas
The parameter is called Free variable ( Conceptual nouns , Understanding can ). Function as func
After the end of the declaration cycle ,parmas
This variable still exists , The reason is that the closed function inner_func
Called , So it won't be recycled .
After simply learning closure operation , You will find that closure operations , stay Last blog It has been used , The description of the blog is Decorator .
Comment on the above code again , Help you understand the implementation of closure functions .
# Define external ( Outer layer ) function def func(parmas): # Internal definition ( Inner layer ) function def inner_func(p): print(f" External function parameters {parmas}, Internal function parameters {p}") # Be sure to return the inner function return inner_func # Call outer function , Assign to a new variable inner, At this time inner Equivalent to inner function , And keep the free variables params inner = func(" Outside ") inner(" Inside ")
Sum up , Implementing a closure requires the following steps :
Look at the code first :
def outer_func(): my_list = [] def inner_func(x): my_list.append(len(my_list)+1) print(f"{x}-my_list:{my_list}") return inner_func test1 = outer_func() test1("i1") test1("i1") test1("i1") test1("i1") test2 = outer_func() test2("i2") test2("i2") test2("i2") test2("i2")
Free variables in the above code my_list
Scope of action , Only with every call to the outer function , Generated variables , The variables referenced by each instance of the closure do not interfere with each other .
As mentioned above , Have you got a preliminary understanding of the function of closures ?
Now let me emphasize , Scope related issues will be involved in closure operations , The ultimate goal is to get out of the scope of the function itself , Local variables can also be accessed .
def outer_func(): msg = " Dream eraser " def inner_func(): print(msg) return inner_func outer = outer_func() outer()
If you still have an impression of the snowball for the first time , You will learn that local variables are only available during the execution of the function , That is to say outer_func
After the function is executed ,msg
Variables are not available , But the above implementation outer_func
after , Call again outer
When ,msg
Variables are also output , That's what closures do , Closures enable local variables to be accessed outside functions .
The corresponding theory is further expanded , In this case, local variables can be used as global variables .
Finally, I would like to make a remark , Explain the function of closures : Closure , Save some non global variables , That is, save local information without being destroyed .
adopt Function name .__closure__
Determine whether a function is a closure function .
def outer_func(): msg = " Dream eraser " def inner_func(): print(msg) return inner_func outer = outer_func() outer() print(outer.__closure__)
(<cell at 0x0000000002806D68: str object at 0x0000000001D46718>,)
In the tuple returned , The first is CELL
That is, the closure function .
This problem is the problem of address and value , It is a problem caused by the underlying principles of the operating system , See the code first , A very classic case .
def count(): fs = [] for i in range(1, 4): def f(): return i fs.append(f) return fs f1, f2, f3 = count() print(f1()) print(f2()) print(f3())
The above code does not simply return a closure function , Instead, it returns a sequence of three closure functions list
.
Run code , Output 3 individual 3, Students who have learned the knowledge of quotation and value will be easier to master , In the above code i
It points to an address , It's not a specific value , This leads to when the loop ends ,i
The value pointing to that address is equal to 3
.
In this case, you can also remember the following sentence .
Try to avoid referencing loop variables in closures , Or variables that will change in the future .
This blog provides you with some basic knowledge about closures , Learn together with the last decorator blog , The effect is more .