> -------------------------------- > def doLambda(val): > print "value 2:", val > > commands = [] > for value in range(5): > print "value 1:", value > commands.append(lambda:doLambda(value)) > > for c in commands: > c()
Hi Fred, Ah, this one of those unfrequently asked questions. lambdas in Python's for loop are a little tricky because the for loop rebinds the element variable. That is, what's happening is that all those lambda functions are just resetting the same 'value' variable: the loop is merely rebinding value to the elements of range(5). All the lambdas are sharing the same name binding, and that explains why we see this kind of aliasing behavior. One possible fix is to do this: ###### def makeDoLambda(value): def f(): return doLambda(value) return f ###### Once we have this makeDoLambda() function, then we can use it: commands.append(makeDoLambda(value)) The act of calling the makeDoLambda() function makes a fresh name binding to 'value', so that none of the lambda functions share the same binding. Another way to do this is to force our lambda to make a fresh binding with a default parameter: commands.append(lambda v=value: doLambda(v)) This is subtle, so if you have more questions, please feel free to ask. Slightly off-topic footnote: if you're familiar with the Scheme programming language, then what's happening can be simulated like this: ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; ;;; Simulates some of the essence of Python's for loop (define-syntax python-for-each (syntax-rules () ((_ (id list) e1 e2 ...) (let ((id #f)) (let loop ((L list)) (if (null? L) (void) (begin (set! id (car L)) e1 e2 ... (loop (cdr L))))))))) (begin (define commands '()) (python-for-each (i '(1 2 3 4 5)) (set! commands (cons (lambda () i) commands))) (for-each (lambda (f) (display (f)) (newline)) commands)) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; Python's loop has set!-ish behavior, and it's that rebinding behavior that causes the issues you are seeing. _______________________________________________ Tutor maillist - Tutor@python.org http://mail.python.org/mailman/listinfo/tutor