Поведение Лямбды Python

Я пытаюсь получить голову вокруг лямбда-выражений, закрытий и определяющий объем в Python. Почему программа не отказывает на первой строке здесь?

>>> foo = lambda x: x + a
>>> foo(2)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 1, in <lambda>
NameError: global name 'a' is not defined
>>> a = 5
>>> foo(2)
7
>>> 
5
задан ntimes 19 February 2010 в 04:52
поделиться

5 ответов

Потому что так не работают функции Python; это не особенность лямбд:

>>> def foo(x):
...   return x + a
>>> foo
<function foo at 0xb7dde454>
>>> foo(2)
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 2, in foo
NameError: global name 'a' is not defined

Переменные ищутся при использовании, а не при определении функции. Они даже ищутся каждый раз при вызове функции, что покажется вам неожиданным, если вы работаете на языке C (например), но в Python это не проблема.

6
ответ дан 13 December 2019 в 22:06
поделиться

Ваше лямбда-выражение не вычисляется, пока вы его не вызовете.

Он анализируется, поэтому синтаксическая ошибка может вызвать обратную трассировку.

>>> foo = lambda x : x + a
>>> bar = lambda y : print y
SyntaxError: invalid syntax
2
ответ дан 13 December 2019 в 22:06
поделиться

Переменные в Python могут быть использованы до того, как они установлены. Это приведет к ошибке времени выполнения, а не к синтаксической ошибке. Вот пример использования локальных переменных:

>>> def f():
...     return a
...     a = 3
... 
>>> f()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 2, in f
UnboundLocalError: local variable 'a' referenced before assignment

В отличие от языков, в которых разыменование неназначенной или неопределенной переменной считается синтаксической ошибкой. Python не "фиксирует" текущее состояние лексической области видимости, он просто использует ссылки на изменяемые лексические области видимости. Вот демонстрация:

>>> def f(): return a
... 
>>> f()
Traceback (most recent call last):
  File "<stdin>", line 1, in <module>
  File "<stdin>", line 1, in f
NameError: global name 'a' is not defined
>>> a = 3
>>> f()
3
2
ответ дан 13 December 2019 в 22:06
поделиться

Тела лямбда-выражений (и функций, определенных с помощью def) в Python не оцениваются до тех пор, пока они не будут вызваны. Имена всегда просматриваются во время выполнения.

0
ответ дан 13 December 2019 в 22:06
поделиться

в первой строке вы создаете выражение, что отличается от его оценки. Когда вы пытаетесь оценить его, оно не может найти символ a.

0
ответ дан 13 December 2019 в 22:06
поделиться
Другие вопросы по тегам:

Похожие вопросы: