Unintelligible Lambda Tricks

Gerson Kurz gerson.kurz at t-online.de
Thu Feb 21 23:20:00 EST 2002


On Thu, 21 Feb 2002 19:44:34 -0800, chajadan <python at chajadan.net>
wrote:

>data.__setitem__(4,42)
>
>def swap(a,x,y):
>a[x] = (a[x], a[y])
>a[y] = a[x][0]
>a[x] = a[x][1]
>You can write this as a lambda expression like this:
>
>>swap = lambda a,x,y:(lambda
>>f=a.__setitem__:(f(x,(a[x],a[y])),f(y,a[x][0]),f(x,a[x][1])))()
>
>I don't understand why __setitem__ takes 2 arguments, but in the lambda () 
>there are 3...

Well, it doesn't? Its a matter of bracket counting. Here is what the
expression does:

swap = lambda a,x,y:(lambda
f=a.__setitem__:(f(x,(a[x],a[y])),f(y,a[x][0]),f(x,a[x][1])))()

Take out these parts:

part_1 = f(x,(a[x],a[y]))
part_2 = f(y,a[x][0])
part_3 = f(x,a[x][1])

Those are our three swap statements from above. Note that part_1 is a
function that takes a tuple of *two* elements: x, and a tuple. Its not
three elements! This is just like the code in the "regular" swap()
function above. 

So you can think of the lambda as

swap = lambda a,x,y:(lambda f=a.__setitem__:(part_1,part_2,part_3))()

(this is not valid python, its just to show the structure of the
code). Next, the inner lambda function is just a helper. By defining

lambda f=a.__setitem__:(expression that uses f)

I define a function that can use "f" in any place it would have to
write a.__setitem__. Writing three times "f" is shorter than writing
three times "a.__setitem__". To invoke that expression, include it in
brackets and add a (), as in 

(function-declaration)()

so, mystery solved, I hope ;)







More information about the Python-list mailing list