0

Why is the lambda expression only outputting the same result?
I expected to get the current value of the iterator and therefore the lambda expressions would output the numbers from 1 to 4 but that is obviously not the case.
I assume that the problem may have something to do with how the iterator is treated by the lambda expression but i could not find a answer to it yet. Thank you in advance

list = []
for i in range(5):
    list.append(lambda:i)
for a in list:
    print(a())

---OUTPUT---
4
4
4
4
martineau
  • 119,623
  • 25
  • 170
  • 301
  • 1
    Terminology note: `i` is **not an iterator**, iterator is not the correct term for this in Python. An iterator has a specific meaning. E.g. `iter(some_object)` returns *an iterator*, and object that defines both an `__iter__` and a `__next__` method is an iterator. – juanpa.arrivillaga Jan 11 '21 at 15:10
  • See e.g. https://stackoverflow.com/q/19837486/3001761 (via https://sopython.com/canon/30/why-do-my-lambda-functions-or-nested-functions-created-in-a-loop-all-use-the-las/) – jonrsharpe Jan 11 '21 at 15:11
  • Anyway, in your function, `i` refers to the *variable `i` in the global scope*. When you call `a()`, what is the value of `i`? it is `4`. Think about it this way, why do you expect this to be different than `print(i)`? So consider, `def foo(): print(i)` then `i = 0; foo(); i = 10; foo()` – juanpa.arrivillaga Jan 11 '21 at 15:12
  • You're creating closures (or referencing a global), so when you invoke `a()`, you're getting the *current* value of `i`, rather than the value of `i` at the time the lambda was created. You can fix it by changing `lambda: i` to `lambda i=i: i`, which will capture the value of `i` at the time the lambda is created. – Tom Karzes Jan 11 '21 at 15:13
  • @TomKarzes to be pedantic, no closure is actually created here, it's a global variable, but it would work the same in an enclosing scope – juanpa.arrivillaga Jan 11 '21 at 15:14
  • @juanpa.arrivillaga Well, that's assuming the code isn't being executed from within a function, but yeah, if it's a global, then it doesn't create a closure. OP didn't provide any info on the context in which it's being executed. – Tom Karzes Jan 11 '21 at 15:15
  • Thank you very much for the helping and simple answers – Jonas Werner Jan 11 '21 at 15:16

0 Answers0