локальная область python

Запуск этого кода:

import re
regex = re.compile("hello")
number = 0
def test():
  if regex.match("hello"):
    number += 1

test()

Выдает эту ошибку:

Traceback (most recent call last):
  File "test.py", line 12, in <module>
    test()
  File "test.py", line 10, in test
    number += 1
UnboundLocalError: local variable 'number' referenced before assignment

Почему я могу ссылаться на regex внутри функции, но не на number?


person Jangler    schedule 15.02.2013    source источник
comment
Вы также должны прочитать python Часто задаваемые вопросы, где на этот вопрос уже был дан ответ. А если вы хотите узнать больше, вот статья, которая делает именно это.   -  person root    schedule 15.02.2013


Ответы (1)


Потому что вы определяете новую переменную с именем number внутри функции.

Вот что эффективно делает ваш код:

def test():
    if regex.match("hello"):
        number = number + 1

Когда Python впервые компилирует эту функцию, как только он видит number =, это делает number локальным. Любая ссылка на number внутри этой функции, независимо от того, где она появляется, будет ссылаться на новый локальный объект. Глобальное затенено. Поэтому, когда функция фактически выполняется и вы пытаетесь вычислить number + 1, Python обращается к local number, которому еще не присвоено значение.

Это все из-за отсутствия в Python объявления переменных: поскольку вы не объявляете локальные переменные явно, все они объявляются неявно в верхней части функции.

В этом случае вы можете использовать global number (в отдельной строке), чтобы сообщить Python, что вы всегда хотите обращаться к глобальному number. Но часто лучше вообще не нуждаться в этом. Вы хотите совместить какое-то поведение с каким-то состоянием, и именно для этого и нужны объекты, поэтому вы можете просто написать небольшой класс и создать его экземпляр только один раз.

person Eevee    schedule 15.02.2013
comment
+1 в основном за упоминание о том, что лучше избегать глобальных переменных (что выделяет этот ответ). - person Demian Brecht; 15.02.2013