Вопрос-Ответ

What does "nonlocal" do in Python 3?

Что делает "нелокальный" в Python 3?

Что nonlocal делает в Python 3.x?


Чтобы закрыть вопросы отладки, в которых OP нуждается nonlocal и не осознает этого, пожалуйста, используйте Возможно ли изменить переменную в python, которая находится во внешней, но не глобальной области видимости? вместо этого.

Хотя Python 2 официально не поддерживается с 1 января 2020 года, если по какой-либо причине вы вынуждены поддерживать кодовую базу Python 2.x и вам нужен эквивалент nonlocal, см. Ключевое слово nonlocal в Python 2.x.

Переведено автоматически
Ответ 1

Сравните это, не используя nonlocal:

x = 0
def outer():
x = 1
def inner():
x = 2
print("inner:", x)

inner()
print("outer:", x)

outer()
print("global:", x)

# inner: 2
# outer: 1
# global: 0

Для этого используется nonlocal, где inner()'s x теперь также outer()'s x:

x = 0
def outer():
x = 1
def inner():
nonlocal x
x = 2
print("inner:", x)

inner()
print("outer:", x)

outer()
print("global:", x)

# inner: 2
# outer: 2
# global: 0

Если бы мы использовали global, это привязывало бы x к правильно "глобальному" значению:

x = 0
def outer():
x = 1
def inner():
global x
x = 2
print("inner:", x)

inner()
print("outer:", x)

outer()
print("global:", x)

# inner: 2
# outer: 1
# global: 2
Ответ 2

Короче говоря, он позволяет присваивать значения переменной во внешней (но неглобальной) области видимости. Смотрите PEP 3104 для получения всех подробностей.

Ответ 3

Поиск в Google по запросу "python нелокальный" выдал предложение, PEP 3104, которое полностью описывает синтаксис и рассуждения, стоящие за оператором. короче говоря, он работает точно так же, как оператор global, за исключением того, что он используется для обращения к переменным, которые не являются ни глобальными, ни локальными для функции.

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

def make_counter():
count = 0
def counter():
nonlocal count
count += 1
return count
return counter

Очевидно, вы могли бы написать это как генератор, например:

def counter_generator():
count = 0
while True:
count += 1
yield count

Но хотя это совершенно идиоматичный python, кажется, что первая версия была бы немного более очевидной для новичков. Правильное использование генераторов путем вызова возвращаемой функции является распространенной причиной путаницы. Первая версия явно возвращает функцию.

Ответ 4

Он использует тот, который "ближе всего" к точке отсчета в исходном коде. Это называется "Лексическая область видимости" и является стандартом уже более 40 лет.

Члены класса Python на самом деле находятся в словаре с именем __dict__ и никогда не будут доступны с помощью лексической области видимости.

Если вы не укажете, nonlocal но сделаете x = 7, это создаст новую локальную переменную "x". Если вы укажете nonlocal, он найдет "ближайший" "x" и присвоит ему значение. Если вы укажете nonlocal, а "x" нет, он выдаст вам сообщение об ошибке.

Ключевое слово global всегда казалось мне странным, поскольку оно с радостью игнорирует все остальные "x", кроме самого внешнего.

python