I cannot find out what key=key
does in this simple python code:
for key in dict:
f = (lambda key=key: print(key))
print(f())
I cannot find out what key=key
does in this simple python code:
for key in dict:
f = (lambda key=key: print(key))
print(f())
In this piece of code, key=key
does nothing useful at all. You can just as well write the loop as
for key in [1,2,3]:
f = lambda: key
print(f())
This will print 1
, 2
, and 3
. (Note that -- unrelated to the problem -- I also removed the print
from the lambda
, instead returning the value directly, because it's redundant and will only make the "outer" print
print None
, as that's what the function would return with print
.)
But what if you do not execute the function right within the loop, but afterwards?
functions = []
for key in [1,2,3]:
f = lambda: key
functions.append(f)
for f in functions:
print(f())
Now, this will print 3
, 3
, and 3
, as the key
variable is evaluated when the function is called, not when it is defined, i.e. after the loop when it has the value 3
. This can lead to some serious surprises e.g. when defining callback functions for different buttons in a loop.
Here, using key=key
comes into play: This will create a parameter key
and assign to it the current value of the key
variable in the loop when the function is defined as a default value (hence you do not have to pass a parameter when calling the function). The value of that key
paremeter will then stay the same within the scope of the function when the function is called later:
functions = []
for key in [1,2,3]:
f = lambda key=key: key
functions.append(f)
This prints 1
, 2
, and 3
, as would be expected. As others have noted, you can use a different name for the parameter, to make this less confusing, e.g. f = lambda param=key: param
.
This code is not "simple", it's actually somewhat tricky to understand for a Python novice.
The for key in dict:
simply loops over what dict
is. Normally dict
is a predefined system library class (the class of standard dictionaries) and iterating over a class object is (normally) nonsense.
Python however allows to redefine what dict
is bound to: dict
is not a keyword, but just a regular name that can be reused as you like - if you like to write bad python code that confuses IDEs and fellow programmers.
I'll assume that dict
in this context is some kind of container that can be iterated over: it could be a list, a tuple or a dictionary (as the name suggests) for example. Note that iterating over a dictionary means in Python iterating over dictionary keys.
f = (lambda key=key: print(key))
this code creates an unnamed function that accepts a parameter named key
, and defines the default value to be current value of variable key
used in the loop. The body of the function simply calls the standard print
function passing key
as argument.
The code is equivalent to:
f = lambda x=key: print(x)
that is probably a bit clearer for a novice because avoids reusing the same name.
Finally at each iteration this function is called passing no parameters and the result is sent to print
standard function. The evaluation of f()
will print the key
value (passing no parameters the default value will be used) and the result of print
(that is None
) will be printed by the second print
call.
There is really nothing good about this example. Actually the lambda x=x:...
is a pattern in Python and sometimes is necessary but here is complete nonsense and there's nothing to learn from this use.
You should reconsider continuing reading from the source you got this from (I'd suspect that the rest is bad stuff also). Stick to official tutorials for better examples...