Переменные в Python

Оглавление

В предыдущем уроке Основные типы данных в Python вы увидели, как можно создавать значения различных типов данных Python. Но до сих пор все показанные значения были литеральными или константными:

>>> print(5.3)
5.3

Если вы пишете более сложный код, вашей программе понадобятся данные, которые могут меняться по мере выполнения программы.

Вот что вы узнаете в этом уроке: Вы узнаете, как каждый элемент данных в программе на Python может быть описан абстрактным термином object, и научитесь манипулировать объектами с помощью символических имен, называемых variables.

Назначение переменных

Подумайте о переменной как об имени, прикрепленном к определенному объекту. В Python переменные не нужно объявлять или определять заранее, как это делается во многих других языках программирования. Чтобы создать переменную, достаточно присвоить ей значение, а затем начать ее использовать. Присвоение выполняется с помощью одного знака равенства (=):

>>> n = 300

Это читается или интерпретируется как "n присвоено значение 300". После этого n можно использовать в операторе или выражении, и его значение будет подставлено:

>>> print(n)
300

Так же, как буквальное значение может быть отображено непосредственно из подсказки интерпретатора в сессии REPL без необходимости print(), так и переменная:

>>> n
300

В дальнейшем, если вы измените значение n и используете его снова, вместо него будет подставлено новое значение:

>>> n = 1000
>>> print(n)
1000
>>> n
1000

Python также допускает цепочечное присваивание, что позволяет присваивать одно и то же значение нескольким переменным одновременно:

>>> a = b = c = 300
>>> print(a, b, c)
300 300 300

Приведенное выше цепочечное присваивание присваивает 300 переменным a, b и c одновременно.

Типы переменных в Python

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

На переменные в Python это ограничение не распространяется. В Python переменной может быть присвоено значение одного типа, а затем повторно присвоено значение другого типа:

>>> var = 23.5
>>> print(var)
23.5

>>> var = "Now I'm a string"
>>> print(var)
Now I'm a string

Ссылки на объекты

Что на самом деле происходит, когда вы присваиваете переменную? Это важный вопрос в Python, потому что ответ на него несколько отличается от того, что вы найдете во многих других языках программирования.

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

Рассмотрите этот код:

>>> print(300)
300

Представляя утверждение print(300), интерпретатор делает следующее:

  • Создает целочисленный объект
  • Присваивает ему значение 300
  • Отображает его на консоли

Вы видите, что целочисленный объект создается с помощью встроенной функции type():

>>> type(300)
<class 'int'>

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

Например:

>>> n = 300

Это задание создает целочисленный объект со значением 300 и присваивает переменной n указание на этот объект.

Variable reference diagram

Присвоение переменных

Следующий код проверяет, что n указывает на целочисленный объект:

>>> print(n)
300
>>> type(n)
<class 'int'>

Теперь рассмотрим следующее утверждение:

>>> m = n

Что происходит при его выполнении? Python не создает другой объект. Он просто создает новое символическое имя или ссылку, m, которая указывает на тот же объект, на который указывает n.

Python variable references to the same object (illustration)

Многочисленные ссылки на один объект

Далее, предположим, вы сделаете следующее:

>>> m = 400

Теперь Python создает новый целочисленный объект со значением 400, а m становится ссылкой на него.

References to separate objects in Python (diagram)

Ссылки на отдельные объекты

И, наконец, предположим, что этот оператор будет выполнен следующим образом:

>>> n = "foo"

Теперь Python создает объект string со значением "foo" и заставляет n ссылаться на него.

Python variable reference illustration

Осиротевший объект

Больше не существует ссылок на целочисленный объект 300. Он осиротел, и нет способа получить к нему доступ.

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

Когда количество ссылок на объект падает до нуля, он становится недоступным. В этот момент время его жизни заканчивается. В конце концов Python заметит, что объект недоступен, и вернет ему выделенную память, чтобы использовать ее для чего-то другого. На компьютерном жаргоне этот процесс называется сборкой мусора.

Идентичность объекта

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

Встроенная функция Python id() возвращает целочисленный идентификатор объекта. С помощью функции id() можно проверить, что две переменные действительно указывают на один и тот же объект:

>>> n = 300
>>> m = n
>>> id(n)
60127840
>>> id(m)
60127840

>>> m = 400
>>> id(m)
60127872

После присваивания m = n, m и n указывают на один и тот же объект, что подтверждается тем, что id(m) и id(n) возвращают одно и то же число. После того как m переназначается на 400, m и n указывают на разные объекты с разными идентификаторами.

Глубокое погружение: Кэширование небольших целочисленных значений

Из того, что вы теперь знаете о присвоении переменных и объектных ссылках в Python, следующее, вероятно, не удивит вас:

>>> m = 300
>>> n = 300
>>> id(m)
60062304
>>> id(n)
60062896

С помощью оператора m = 300 Python создает целочисленный объект со значением 300 и устанавливает m в качестве ссылки на него. Затем n аналогичным образом присваивается целочисленному объекту со значением 300, но не тому же самому объекту. Таким образом, они имеют разные идентификаторы, в чем вы можете убедиться по значениям, возвращаемым id().

Но рассмотрим следующее:

>>> m = 30
>>> n = 30
>>> id(m)
1405569120
>>> id(n)
1405569120

Здесь m и n отдельно присваиваются целочисленным объектам, имеющим значение 30. Но в этом случае id(m) и id(n) идентичны!

В целях оптимизации интерпретатор создает объекты для целых чисел в диапазоне [-5, 256] при запуске, а затем повторно использует их во время выполнения программы. Таким образом, когда вы присваиваете отдельным переменным целое значение из этого диапазона, они фактически будут ссылаться на один и тот же объект.

Имена переменных

В примерах, которые вы видели до сих пор, использовались короткие, лаконичные имена переменных, такие как m и n. Но имена переменных могут быть и более многословными. На самом деле, это обычно полезно, так как делает назначение переменной более очевидным с первого взгляда.

Официально имена переменных в Python могут быть любой длины и состоять из прописных и строчных букв (A-Z, a-z), цифр (0-9) и символа подчеркивания (_). Дополнительным ограничением является то, что, хотя имя переменной может содержать цифры, первый символ имени переменной не может быть цифрой.

Примечание: Одним из дополнений к Python 3 стала полная поддержка Unicode, которая позволяет использовать символы Unicode и в имени переменной. Более подробно о Unicode вы узнаете в одном из следующих уроков.

Например, все следующие имена переменных являются допустимыми:

>>> name = "Bob"
>>> Age = 54
>>> has_W2 = True
>>> print(name, Age, has_W2)
Bob 54 True

Но это не так, потому что имя переменной не может начинаться с цифры:

>>> 1099_filed = False
SyntaxError: invalid token

Обратите внимание, что регистр имеет значение. Строчные и прописные буквы - это не одно и то же. Также имеет значение использование символа underscore. Каждый из следующих символов определяет отдельную переменную:

>>> age = 1
>>> Age = 2
>>> aGe = 3
>>> AGE = 4
>>> a_g_e = 5
>>> _age = 6
>>> age_ = 7
>>> _AGE_ = 8

>>> print(age, Age, aGe, AGE, a_g_e, _age, age_, _AGE_)
1 2 3 4 5 6 7 8

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

Стоит дать переменной достаточно описательное имя, чтобы было понятно, для чего она используется. Например, предположим, что вы подсчитываете количество людей, окончивших колледж. Вы можете выбрать любое из следующих вариантов:

>>> numberofcollegegraduates = 2500
>>> NUMBEROFCOLLEGEGRADUATES = 2500
>>> numberOfCollegeGraduates = 2500
>>> NumberOfCollegeGraduates = 2500
>>> number_of_college_graduates = 2500

>>> print(numberofcollegegraduates, NUMBEROFCOLLEGEGRADUATES,
... numberOfCollegeGraduates, NumberOfCollegeGraduates,
... number_of_college_graduates)
2500 2500 2500 2500 2500

Все они, вероятно, являются лучшим выбором, чем n, или ncg, или т.п. По крайней мере, по имени можно определить, что должно представлять собой значение переменной.

С другой стороны, все они не обязательно одинаково разборчивы. Как и во многих других случаях, это вопрос личных предпочтений, но большинство людей сочтут первые два примера, в которых все буквы сдвинуты вместе, более трудными для чтения, особенно тот, который написан заглавными буквами. Наиболее часто используемые методы построения многословных имен переменных - это три последних примера:

  • Camel Case: второе и последующие слова пишутся с заглавной буквы, чтобы легче было увидеть границы слов. (Предположительно, кому-то в какой-то момент показалось, что заглавные буквы, разбросанные по всему имени переменной, смутно напоминают верблюжьи горбы).
    • Пример: numberOfCollegeGraduates
  • Pascal Case: идентичен верблюжьему регистру, за исключением того, что первое слово также пишется с заглавной буквы.
    • Пример: NumberOfCollegeGraduates
  • Snake Case: Слова разделяются подчеркиванием.
    • Пример: number_of_college_graduates

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

Позже вы увидите, что переменные - это не единственные вещи, которым можно давать имена. Вы также можете давать имена функциям, классам, модулям и так далее. Правила, применяемые к именам переменных, также применимы к идентификаторам - более общему термину для имен, присваиваемых объектам программы.

В Style Guide for Python Code, также известном как PEP 8, содержится Naming Conventions, в котором перечислены предлагаемые стандарты для имен различных типов объектов. PEP 8 включает следующие рекомендации:

Запасные слова (ключевые слова)

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

В Python 3.6 существует 33 зарезервированных ключевых слова:

Python
Keywords
     
False def if raise
None del import return
True elif in try
and else is while
as except lambda with
assert finally nonlocal yield
break for not  
class from or  
continue global pass  

Вы можете посмотреть этот список в любое время, набрав help("keywords") в интерпретаторе Python. Зарезервированные слова чувствительны к регистру и должны использоваться именно так, как показано на рисунке. Все они полностью строчные, за исключением False, None и True.

Попытка создать переменную с именем, совпадающим с любым зарезервированным словом, приводит к ошибке:

>>> for = 3
SyntaxError: invalid syntax

Заключение

В этом уроке рассмотрены основы Python переменных, включая объектные ссылки и идентификацию, а также именование идентификаторов Python.

Теперь вы хорошо понимаете некоторые типы данных Python и знаете, как создавать переменные, ссылающиеся на объекты этих типов.

Далее вы увидите, как объединять объекты данных в выражения, включающие различные операции.

  • Для имен функций и переменных следует использовать змеиный регистр.
  • Для имен классов следует использовать паскальный регистр. (В PEP 8 это называется соглашением "CapWords".)
Вернуться на верх