Область видимости
Область видимости переменных в языке программирования Python представляет собой некое пространство имен, в рамках которого функционируют созданные объекты. Эта особенность позволяет ограничивать доступ к определенным значениям во избежание конфликтов между одинаковыми идентификаторами. Переменные бывают двух видов: локальные и глобальные, что в большинстве случае определяется местом их первичной идентификации в программе.
Локальные переменные
Для создания переменных, обладающих локальной областью видимости, необходимо всего лишь поместить их в отдельный блок кода, изолированный от остальной программы. Чтобы увидеть локальную переменную в действии, достаточно инициализировать целочисленный объект с именем x и значением 100 в функции f, как это сделано в следующем примере:
Здесь x имеет локальную область видимости, так как доступна лишь в рамках своей функции f. Вызывая данную функцию из внешней части программы, можно увидеть вывод целочисленного значения на экране. Однако, если попытаться вывести переменную x при помощи метода print вне зоны действия функции f, компилятор тут же выдаст ошибку:
Так происходит из-за того, что внешняя часть программы ничего не знает о переменной x, поскольку содержит в себе совсем другое пространство имен. Пользоваться локальными объектами можно только в той области, где они были идентифицированы. В обратном же случае компилятор сообщит об ошибке, не сумев обнаружить необходимую переменную.
Глобальные переменные
Чтобы иметь возможность использовать некоторое значение в любой части программы, следует объявить глобальную переменную. Для этого понадобиться создать переменную отдельно от области кода, ограниченной определенным блоком кода, например, функцией. В следующем примере демонстрируется идентификация целочисленного типа данных под названием x, который позже выводится на экран при помощи метода print в функции f:
Как можно заметить из результатов выполнения программы, значение 100 воспроизводится не только через f, но и с помощью обычного print. Таким образом, получение доступа к x осуществляется из любой части кода, благодаря глобальной области видимости подобного объекта. Но что будет, если попытаться изменить значение глобальной переменной в некой функции? Результаты такого эксперимента представлены в следующем фрагменте кода:
Функция f присваивает значение 200 переменной с именем x, однако, вопреки ожиданиям, внешний метод print выводит число 100, которое принадлежало x изначально. Происходит так потому, что в данной программе создаются два разных объекта x с локальной, а также глобальной областью видимости. Исправить ситуацию поможет ключевое слово global:
Пометив переменную x как global, можно обращаться к ее изначальному значению, которое было определено вне зоны действия функции f. Теперь после того как в x поместили число 200, вызов метода print выводит вполне ожидаемый результат, то есть измененное значение.
Но все таки не стоит злоупотреблять. Зачастую гораздо правильнее передавать в функции необходимые значения в качестве аргуменов, а если нужно перезаписать какое-то глобальное значение, то возвращать его из функции.
Нелокальные переменные
Итак, для обращения к глобальной переменной внутри функции f необходимо использовать ключевое слово global перед ее идентификатором. Но что если требуется вызывать совсем не глобальную, а переменную, которая была определена во внешнем методе, являясь при этом локальной для другого пространства имен, находящегося на уровень выше? Следующий код демонстрирует попытку взаимодействия со значением из внешней функции f1 в методе f2:
Несмотря на то, что переменной с таким же именем x было присвоено новое значение 200, в результате выполнения написанных методов на экране отобразилось 100. Как и в том случае с двумя разными переменными, локальной и глобальной, здесь имеется также два различных объекта, которые идентифицированы в отдельных блоках кода. Чтобы обратиться к объекту, который не является локальным, необходимо воспользоваться модификатором nonlocal:
Таким образом, в методе f2 осуществляется запись значения 200 в переменную x из функции f1. В результате подобных действий, вызов метода f1 из внешней части программы создает новую переменную x, значение которой меняется в f2 со 100 на 200 и выводится при помощи print.
Видимость из загружаемого модуля
Теперь разберемся с видимостью глобальных переменных между загружаемыми модулями Python. Например, мы подключаем другой модуль с помощью команды import. Создадим файл «test.py» и в него запишем следующий код:
То есть мы определили глобальную переменную x для модуля test. Так же определили функцию, которая выводит на экран её значение.
Теперь создадим файл main.py, который и будем запускать. В нем мы импортируем модуль test, а так же создадим свою глобальную переменную x. После этого выведем значения глобальной переменной из test, вызовим функцию f, а так же проверим, что значение переменной в модуле main не изменилось:
Мы в первой же строчке записали в x значение 200. Это было сделано, чтобы показать, что после того, как мы загрузим внешний модуль, значение этой переменной не изменится. Так и вышло. Обращаясь к переменной из загруженной библиотеки, удалось прочитать его и изменить значение.
Теперь модифицируем программу следующим образом:
В этом случае для загрузки мы использовали команду «from test import *». Мы импортировали все переменные и функции. После загрузки модуля значение переменной x в модуле main изменилось. Но при вызове функции, мы получаем значение x из модуля test. После присвоения нового значения переменной x, значение, которое выводит функция f не изменяется.
Глобальные переменные в классе
Точно так же как и в функциях, можно обращаться к глобальным переменным и в классе Python. Разберем пример:
Мы объявили глобальную переменную x. Вывели значение переменной до и после объявления класса. Как видим значение изменилось. После того как мы создали объект класса, значение в очередной раз поменялось. Это произошло, потому что сработал конструктор класса — метод __init__. После вызова функции f у созданного объекта, значение стало 400. В Python использование global переменная и в функции класса, и в его конструкторе, и после описания класса дают возможность изменения глобальной переменной. Если убрать это объявление, то тогда выполнится присвоение локальной переменной.
Конечно же если мы определим локальную переменную в классе, то к ней не будет возможности доступа из другого класса:
Для того, чтобы код работал, переменная x должна быль глобальной.
Заключение
Таким образом, область видимости переменных в языке программирования Python, является важной составляющей платформы. Правильное взаимодействие со всеми ее особенностями позволяет избежать множества довольно сложных ошибок. Для более безопасного контроля над видимостью отдельных объектов применяются ключевые слова global и nonlocal. Чтобы ознакомиться с дополнительными сведениями по данной теме, следует изучить PEP 3104.
Локальные и глобальные переменные
В программировании особое внимание уделяется концепции о локальных и глобальных переменных, а также связанное с ними представление об областях видимости. Соответственно, локальные переменные видны только в локальной области видимости, которой может выступать отдельно взятая функция. Глобальные переменные видны во всей программе. «Видны» – значит, известны, доступны. К ним можно обратиться по имени и получить связанное с ними значение.
К глобальной переменной можно обратиться из локальной области видимости. К локальной переменной нельзя обратиться из глобальной области видимости, потому что локальная переменная существует только в момент выполнения тела функции. При выходе из нее, локальные переменные исчезают. Компьютерная память, которая под них отводилась, освобождается. Когда функция будет снова вызвана, локальные переменные будут созданы заново.
Вернемся к нашей программе из прошлого урока, немного упростив ее для удобства:
Сколько здесь переменных? Какие из них являются глобальными, а какие – локальными?
К локальной области относятся тела функций. Если, находясь в глобальной области видимости, мы попытаемся обратиться к локальной переменной, то возникнет ошибка:
Однако мы можем обращаться из функций к глобальным переменным:
Наши функции не совсем идеальны. Они должны вычислять площади фигур, но выводить результат на экран им не следовало бы. Вполне вероятна ситуация, когда результат нужен для внутренних нужд программы, для каких-то дальнейших вычислений, а выводить ли его на экран – вопрос второстепенный.
Если функции не будут выводить, а только вычислять результат, то его надо где-то сохранить для дальнейшего использования. Для этого подошли бы глобальные переменные. В них можно записать результат. Напишем программу вот так:
Итак, мы ввели в программу глобальную переменную result и инициировали ее нулем. В функциях ей присваивается результат вычислений. В конце программы ее значение выводится на экран. Мы ожидаем, что программа будет прекрасно работать. Однако…
… что-то пошло не так.
Когда функция завершает свою работу, то значение локальной result теряется, а глобальная не была изменена.
На самом деле можно принудительно обратиться к глобальной переменной. Для этого существует команда global :
В таком варианте программа будет работать правильно.
Однако менять значения глобальных переменных в теле функции – плохая практика. В больших программах программисту трудно отследить, где, какая функция и почему изменила их значение. Программист смотрит на исходное значение глобальной переменной и может подумать, что оно остается таким же. Сложно заметить, что какая-то функция поменяла его. Подобное ведет к логическим ошибкам.
Чтобы избавиться от необходимости использовать глобальные переменные, для функций существует возможность возврата результата своей работы в основную ветку программы. И уже это полученное из функции значение можно присвоить глобальной переменной в глобальной области видимости. Это делает программу более понятной.
Как функция принимает и возвращает данные, будет рассмотрено в следующих уроках.
Практическая работа
В языке Python можно внутри одной функции определять другую. Напишите программу по следующему описанию.
Как вы думаете, можно ли из основной ветки программы вызвать функцию, вложенную в другую функцию? Почему?
Примеры решения и дополнительные уроки в android-приложении и pdf-версии курса
Переменные Python: объявление, объединение, глобальные и локальные
Дата публикации: 2019-06-14
От автора: что такое переменная в Python? Переменная Python является зарезервированной ячейкой памяти для хранения значений. Другими словами, переменная в программе Python передает данные на компьютер для обработки.
Каждое значение в Python имеет тип данных. Различные типы данных в Python: Numbers, List, Tuple, Strings, Dictionary и т. д. Переменные могут быть объявлены с любым именем или даже буквами, например, a, aa, abc и т. д. В этом руководстве мы узнаем, как:
Объявить и использовать переменную
Повторно объявить переменную
Бесплатный курс «Python. Быстрый старт»
Получите курс и узнайте, как создать программу для перевода текстов на Python
Что такое локальные и глобальные переменные
Как удалить переменную
Как объявить и использовать переменную
Давайте рассмотрим пример. Мы объявим переменную «а» и выведем ее.
Повторное объявление переменной
Вы можете повторно объявить переменную даже после того, как уже объявили ее один раз. Здесь у нас есть переменная, инициализированная как, f =0. Позже мы переназначим для переменной f значение «guru99″.
Пример Python 2
Пример Python 3
Объединение переменных
Посмотрим, сможете ли вы объединить разные типы данных, такие как строка и число. Например, мы объединяем «Guru» с числом «99».
В отличие от Java, который объединяет число со строкой, не объявляя число как строку, Python требует, чтобы число было объявлено как строка, иначе будет отображаться ошибка TypeError.
Для следующего кода вы получите неопределенный вывод:
После того, как целое число объявлено как строка, мы можем объединить в выходных данных «Guru» + str («99″) = «Guru99″.
Локальные и глобальные переменные
В Python, когда вы хотите использовать ту же самую переменную для остальной части вашей программы или модуля, вы объявляете ее глобальной, а если хотите использовать переменную в определенной функции или методе, вы используете локальную переменную.
Давайте разберемся в этой разнице между локальной и глобальной переменными с помощью приведенной ниже программы.
Переменная «f» является глобальной и ей присваивается значение 101, которое выводится.
Переменная f снова объявлена в функции и предполагает локальную область видимости. Ей присваивается значение «I am learning Python.», которое выводится. Эта переменная отличается от глобальной переменной «f», определенной ранее.
Бесплатный курс «Python. Быстрый старт»
Получите курс и узнайте, как создать программу для перевода текстов на Python
После завершения вызова функции локальная переменная f уничтожается. В строке 12, когда мы снова выводим значение «f», оно отображает значение глобальной переменной f =101.
Пример Python 2
Пример Python 3
Используя ключевое слово global, вы можете ссылаться на глобальную переменную внутри функции.
Переменная «f» является глобальной и ей присваивается значение 101, которое выводится на выходе
Переменная f объявляется с использованием ключевого слова global. Это НЕ локальная переменная, но та же глобальная переменная, объявленная ранее. Следовательно, когда мы выводим ее значение, результат равен 101
Мы изменили значение «f» внутри функции. После завершения вызова функции измененное значение переменной «f» сохраняется. В строке 12, когда мы снова выводим значение «f», оно отображает значение «changing global variable»
Пример Python 2
Пример Python 3
Удаление переменной
Вы также можете удалить переменную с помощью команды del «имя переменной». В приведенном ниже примере мы удалили переменную f, и когда мы приступили к ее выводу, мы получили ошибку «variable name is not defined», что означает, что вы удалили переменную.
Заключение:
Переменными называют «конверты» или «контейнеры», в которых может храниться информация. Как и любой другой язык программирования, Python также использует переменную для хранения информации.
Переменные могут быть объявлены любым именем или даже буквами, например, aa, abc и т. д.
Переменные могут быть повторно объявлены даже после того, как вы объявили их один раз
В Python вы не можете объединить строку с числом напрямую, вам нужно объявить их как отдельную переменную, и после этого вы можете объединить число со строкой
Объявляйте локальную переменную, когда хотите использовать ее для текущей функции
Объявляйте глобальную переменную, когда хотите использовать ту же переменную для остальной части программы
Для удаления переменной используется ключевое слово «del».
Редакция: Команда webformyself.
Бесплатный курс «Python. Быстрый старт»
Получите курс и узнайте, как создать программу для перевода текстов на Python
Область видимости и привязка переменной
Введение
Примеры
Глобальные переменные
В Python переменные внутри функций считаются локальными тогда и только тогда, когда они появляются в левой части оператора присваивания или в каком-либо другом случае связывания; в противном случае такая привязка ищется во включающих функциях вплоть до глобальной области видимости. Это верно, даже если оператор присваивания никогда не выполняется.
Обычно, назначение внутри области действия будет скрывать любые внешние переменные с тем же именем:
Локальные переменные
Если имя связывается внутри функции, то по умолчанию доступны только внутри функции:
Нелокальные переменные
Python 3 добавил новое ключевое слово под названием ** нелокальный **. Ключевое слово nonlocal добавляет переопределение области во внутреннюю область. Вы можете прочитать все об этом в [PEP 3104] [1]. Это лучше всего иллюстрируется парой примеров кода. Одним из наиболее распространенных примеров является создание функции, которая может увеличивать:
Если вы попытаетесь запустить этот код, вы получите ** UnboundLocalError * * потому что на переменную ** num ** ссылаются до того, как она назначена в самой внутренней функции. Давайте добавим нелокальный в смесь:
По сути, `nonlocal` позволит вам назначать переменные во внешней области, но не в глобальной области. Таким образом, вы не можете использовать `nonlocal` в нашей функции` counter`, потому что тогда он попытается назначить глобальную область видимости. Попробуйте, и вы быстро получите `SyntaxError`. Вместо этого вы должны использовать `nonlocal` во вложенной функции. (Обратите внимание, что представленная здесь функциональность лучше реализована с использованием генераторов.)
Обязательное вхождение
Функции пропускают область видимости класса при поиске имен
Классы имеют локальную область видимости во время определения, но функции внутри класса не используют эту область при поиске имен. Поскольку лямбда-выражения являются функциями, а их понимание реализуется с использованием области действия функции, это может привести к неожиданному поведению.
Из документации Пайтона на именования и связывания :
В этом примере используются ссылки из этого ответа по Martijn Питерс, который содержит более глубокий анализ этого поведения.
Команда del
Эта команда имеет несколько связанных, но различных форм.
del v
Если v является переменной, команда del v удаляет переменную из ее сферы. Например:
Во всех следующих случаях намерение команды является поведением по умолчанию, но не поддерживается языком. Класс может быть написан таким способом, который лишает законной силы это намерение.
del v.name
Намерение состоит в том, чтобы сделать атрибут name отсутствует. Например:
del v[item]
del v[a:b]
Местный и глобальный охват
Каковы локальные и глобальные возможности?
Объяснение состоит в том, что локальная область действия включает в себя все переменные, определенные в текущей функции, а глобальная область действия включает переменную d, определенную вне текущей функции.
Можно проверить, какие переменные находятся в какой области. Встроенные функции locals() и globals() возвращают целые области как словари.
Что происходит с конфликтами имен?
Для того, чтобы изменить глобальную переменную, используйте ключевое слово global :
Область действия определяется для всего тела функции!
Это означает, что переменная никогда не будет глобальной для половины функции и локальной позже, или наоборот.
Функции внутри функций
Может быть много уровней функций, вложенных в функции, но внутри любой функции есть только одна локальная область действия для этой функции и глобальная область. Там нет промежуточных областей.
Global против nonlocal (Python 3 только)
Оба эти ключевых слова используются для получения доступа на запись к переменным, которые не являются локальными для текущих функций.
Из документации Python на nonlocal :
Нелокальный оператор заставляет перечисленные идентификаторы ссылаться на ранее связанные переменные в ближайшей охватывающей области, исключая глобальные переменные.
Синтаксис
Параметры
Примечания
Научим основам Python и Data Science на практике
Это не обычный теоритический курс, а онлайн-тренажер, с практикой на примерах рабочих задач, в котором вы можете учиться в любое удобное время 24/7. Вы получите реальный опыт, разрабатывая качественный код и анализируя реальные данные.
Все, что вы хотели узнать про области видимости в Python, но стеснялись спросить
В преддверии старта нового потока по курсу «Разработчик Python», решили поговорить про области видимости в Python. Что из этого вышло? — Читайте в материале ниже.
Сегодня мы будем говорить о важных теоретических основах, которые необходимо понимать и помнить, чтобы писать грамотный, читаемый и красивый код. Мы будем вести речь об областях видимости переменных. Эта статья будет полезна не только новичкам, но и опытным программистам, которые пришли в Python из другого языка и хотят разобраться с его механиками работы.
Области видимости определяют, в какой части программы мы можем работать с той или иной переменной, а от каких переменная «скрыта». Крайне важно понимать, как использовать только те значения и переменные, которые нам нужны, и как интерпретатор языка себя при этом ведет. А еще мы посмотрим, как обходить ограничения, накладываемые областями видимости на действия с переменными. В Python существует целых 3 области видимости:
Обычно, речь заходит про области видимости, когда происходит знакомство с функциями. На их примере мы и будем рассматривать работу областей видимости переменных.
Локальная область видимости
Рассмотрим функцию, которая выведет список some_list поэлементно:
Теперь мы поступим следующим образом:
Здесь переменная element внутри функции и переменная с таким же именем вне ее – это две разные переменные, их значения не перекрещиваются и не взаимозаменяются. Они называются одинаково, но ссылаются на разные объекты в памяти. Более того, переменная с именем element внутри функции живет столько же, сколько выполняется функция и не больше. Но будьте аккуратны с тем, чтобы давать локальным и глобальным переменным одинаковые имена, сейчас покажу почему:
Обратите внимание на то, что интерпретатор не указал нам на ошибки. А все потому что sudden_list находится в глобальной области видимости, то есть изнутри функции print_list мы можем к нему обращаться, поскольку изнутри видно то, что происходит снаружи. По причине таких механик работы старайтесь называть локальные переменные внутри функции не так, как называете переменные в глобальной области видимости.
Здесь важно поговорить о константах. Интерпретатору Python нет разницы как вы называете переменную, поэтому код выше будет лучше переписать в следующем виде:
Теперь все на своих местах. Дело в том, что в Python нельзя каким-то образом строго определить константу, как объект, который не должен быть изменен. Так что то, как вы используете значение переменной, имя которой записано заглавными буквами, остается лишь на вашей совести. Другой вопрос, что таким способом записанная переменная даст понять тому, кто будет читать ваш код, что переменная нигде изменяться не будет. Или по крайней мере не должна.
Глобальная область видимости
В результате получим:
Однако менять значение глобальной переменной изнутри функции – не лучшая практика и лучше так не делать, поскольку читаемости кода это не способствует. Чем меньше то, что происходит внутри функции будет зависеть от глобальной области видимости, тем лучше.
Нелокальная область видимости
Насколько это полезно вам предстоит решить самостоятельно. Больше примеров вы можете найти здесь.
В качестве вывода можно сформулировать несколько правил:











