На этом шаге мы рассмотрим, какие особенности возникают из того факта, что функции - это объекты.
Все данные в программе Python представляются объектами или связями между объектами.
Символьные последовательности (строки), списки, модули и функции - все эти явления языка представляют собой объекты. Что касается функций, то в Python они ничем не отличаются. Они - тоже объекты.
Поскольку функция yell() в Python является объектом, вы можете ее присвоить еще одной переменной, точно так же, как это происходит с любым другим объектом:
>>> bark = yell
Эта строка кода не вызывает функцию. Она берет объект-функцию, на который ссылается имя yell, и создает второе имя, bark, которое на него указывает. Теперь вы можете исполнить тот же самый объект-функцию, который лежит в его основе, вызвав bark:
>>> bark('гав') 'ГАВ!'
Объекты-функции и их имена - это две отдельные компетенции. Вот еще одно доказательство. Вы можете удалить первоначальное имя функции (yell), и, поскольку еще одно имя (bark) по-прежнему указывает на лежащую в основе функцию, вы все так же можете через него вызвать эту функцию:
>>> del yell >>> yell('Привет?') Traceback (most recent call last): NameError: name 'yell' is not defined >>> bark('эй') 'ЭЙ!'
Кстати, Python прикрепляет к каждой функции строковый идентификатор. Это делается для отладочных целей во время создания функции. К этому внутреннему идентификатору можно получить доступ посредством атрибута __name__.
>>> bark.__name__
'yell'
Нужно сказать, что хотя атрибут __name__ функции по-прежнему "yell", это не влияет на то, каким образом вы получаете доступ к объекту-функции из вашего программного кода. Идентификатор имени является просто средством отладки. Указывающая на функцию переменная и сама функция обладают совершенно разными компетенциями.
На следующем шаге мы рассмотрим, где могут располагаться функции.