"Укус питона" 🐍
159 subscribers
45 photos
1 file
19 links
A Byte of Python (Russian), Версия 2.02

Официальная страница этой книги находится по адресу https://python.swaroopch.com , где
вы можете прочитать саму книгу, скачать её последнюю версию, купить её печатный вариант и оставить свои отзывы.
Download Telegram
Только ключевые параметры

Если некоторые ключевые параметры должны быть доступны только по ключу, а не как позиционные аргументы, их можно объявить после параметра со звёздочкой (сохраните как keyword_only.py):

def total(initial=5, *numbers, extra_number):
count = initial
for number in numbers:
count += number
count += extra_number
print(count)

total(10, 1, 2, 3, extra_number=50)
total(10, 1, 2, 3)
# Вызовет ошибку, поскольку мы не указали значение
# аргумента по умолчанию для 'extra_number'.

Вывод:

$ python keyword_only.py
66
Traceback (most recent call last):
File "keyword_only.py", line 12, in <module>
total(10, 1, 2, 3)
TypeError: total() needs keyword-only argument extra_number

Как это работает:

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

Обратите внимание на использование +=, который представляет собой сокращённый оператор, позволяющий вместо x = x + y просто написать x += y.

Если вам нужны аргументы, передаваемые только по ключу, но не нужен параметр со звёздочкой, то можно просто указать одну звёздочку без указания имени: def total(initial=5, *, extra_number).
Оператор “return”

Оператор return используется для возврата[5] из функции, т.е. для прекращения её работы и выхода из неё. При этом можно также вернуть некоторое значение из функции.

Пример: (сохраните как func_return.py)

#!/usr/bin/python
# Filename: func_return.py

def maximum(x, y):
if x > y:
return x
elif x == y:
return 'Числа равны.'
else:
return y

print(maximum(2, 3))

Вывод:

$ python func_return.py
3

Как это работает:

Функция maximum возвращает максимальный из двух параметров, которые в данном случае передаются ей при вызове. Она использует обычный условный оператор if..else для определения наибольшего числа, а затем возвращает это число.

Обратите внимание, что оператор return без указания возвращаемого значения эквивалентен выражению return None. None – это специальный тип данных в Python, обозначающий ничего. К примеру, если значение переменной установлено в None, это означает, что ей не присвоено никакого значения.

Каждая функция содержит в неявной форме оператор return None в конце, если вы не указали своего собственного оператора return. В этом можно убедиться, запустив print(someFunction()), где функция someFunction – это какая-нибудь функция, не имеющая оператора return в явном виде. Например:

def someFunction():
pass

Оператор pass используется в Python для обозначения пустого блока команд.

Примечание Существует встроенная функция max, в которой уже реализован функционал “поиск максимума”, так что пользуйтесь этой встроенной функцией, где это возможно.
👍1
Строки документации

Python имеет остроумную особенность, называемую строками документации, обычно обозначаемую сокращённо docstrings. Это очень важный инструмент, которым вы обязательно должны пользоваться, поскольку он помогает лучше документировать программу и облегчает её понимание. Поразительно, но строку документации можно получить, например, из функции, даже во время выполнения программы!

Пример: (сохраните как func_doc.py)

def printMax(x, y):
'''Выводит максимальное из двух чисел.

Оба значения должны быть целыми числами.'''
x = int(x) # конвертируем в целые, если возможно
y = int(y)

if x > y:
print(x, 'наибольшее')
else:
print(y, 'наибольшее')

printMax(3, 5)
print(printMax.__doc__)

Вывод:

$ python func_doc.py
5 наибольшее
Выводит максимальное из двух чисел.

Оба значения должны быть целыми числами.

Как это работает:

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

Строки документации принято записывать в форме многострочной[7] строки, где первая строка начинается с заглавной буквы и заканчивается точкой. Вторая строка оставляется пустой, а подробное описание начинается с третьей. Вам настоятельно рекомендуется следовать такому формату для всех строк документации всех ваших нетривиальных функций.

Доступ к строке документации функции printMax можно получить с помощью атрибута этой функции (т.е. имени, принадлежащего ей) __doc__ (обратите внимание на двойное подчёркивание). Просто помните, что Python представляет всё в виде объектов, включая функции. Мы узнаем больше об объектах в главе о классах.

Если вы пользовались функцией help() в Python, значит вы уже видели строки документации. Эта функция просто-напросто считывает атрибут __doc__ соответствующей функции и аккуратно выводит его на экран. Вы можете проверить её на рассмотренной выше функции: просто включите help(printMax) в текст программы. Не забудьте нажать клавишу q для выхода из справки (help).

Точно так же автоматические инструменты могут получать документацию из программы. Именно поэтому я настоятельно рекомендую вам использовать строки документации для любой нетривиальной функции, которую вы пишете. Команда pydoc, поставляемая вместе с пакетом Python, работает аналогично функции help().
Аннотации

Функции имеют ещё одну дополнительную возможность, называемую аннотациями, которые предоставляют отличный способ сопровождения каждого параметра, равно как и возвращаемого значения дополнительной информацией. Поскольку сам язык Python не интерпретирует эти аннотации каким-либо способом (этот функционал отводится посторонним библиотекам), мы опустим эту возможность из нашего обсуждения. Если вам интересно почитать об аннотациях, просмотрите PEP 3107.
Резюме

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

Далее мы увидим, как использовать и создавать модули Python.
Примечания

[1] “immutable” в терминологии Python (прим. перев.)
[2] times – англ. “раз” (прим. перев.)
[3] say – англ. “сказать” (прим. перев.)
[4] VarArgs – от англ. “Variable number of Arguments” – “переменное число аргументов” (прим. перев.)
[5] return – англ. “возврат” (прим. перев.)
[6] DocString - от англ. “Documentation String” – “строка документации” (прим. перев.)
[7] т.е. строки, содержащей символы перевода строки. (прим. перев)
ГЛАВА V
МОДУЛИ
🕐
МОДУЛИ

Как можно использовать код повторно, помещая его в функции, мы уже видели. А что, если нам понадобится повторно использовать различные функции в других наших программах? Как вы уже, наверное, догадались, ответ – модули.

Существуют разные способы составления модулей, но самый простой – это создать файл с расширением .py, содержащий функции и переменные.

Другой способ – написать модуль на том языке программирования, на котором написан сам интерпретатор Python. Например, можно писать модули на языке программирования C, которые после компиляции могут использоваться стандартным интерпретатором Python.

Модуль можно импортировать в другую программу, чтобы использовать функции из него. Точно так же мы используем стандартную библиотеку Python. Сперва посмотрим, как использовать модули стандартной библиотеки.

Пример: (сохраните как using_sys.py)

import sys

print('Аргументы командной строки:')
for i in sys.argv:
print(i)

print('\n\nПеременная PYTHONPATH содержит', sys.path, '\n')

Вывод:

$ python3 using_sys.py we are arguments
Аргументы командной строки:
using_sys.py
we
are
arguments

Переменная PYTHONPATH содержит ['', 'C:\\Windows\\system32\\python30.zip',
'C:\\Python30\\DLLs', 'C:\\Python30\\lib',
'C:\\Python30\\lib\\plat-win', 'C:\\Python30',
'C:\\Python30\\lib\\site-packages']

Как это работает:

В начале мы импортируем модуль sys командой import. Этим мы говорим Python, что хотим использовать этот модуль. Модуль sys содержит функции, относящиеся к интерпретатору Python и его среде, т.е. к системе (system).

Когда Python выполняет команду import sys, он ищет модуль sys. В данном случае это один из встроенных модулей, и Python знает, где его искать.

Если бы это был не скомпилированный модуль, т.е. модуль, написанный на Python, тогда интерпретатор Python искал бы его в каталогах, перечисленных в переменной sys.path. Если модуль найден, выполняются команды в теле модуля, и он становится доступным. Обратите внимание, что инициализация[1] происходит только при первом импорте модуля.

Доступ к переменной argv в модуле sys предоставляется при помощи точки, т.е. sys.argv. Это явно показывает, что это имя является частью модуля sys. Ещё одним преимуществом такого обозначения является то, что имя не конфликтует с именем переменной argv, которая может использоваться в вашей программе.

Переменная sys.argv является списком строк (списки будут детально обсуждаться в одной из последующих глав). Она содержит список аргументов командной строки, т.е. аргументов, переданных программе из командной строки.

Если вы используете среду разработки[2] для написания и запуска программ, поищите где-нибудь в её меню возможность передавать параметры командной строки.

В нашем примере, когда мы запускаем “python using_sys.py we are arguments”, мы запускаем модуль using_sys.py командой python, а всё, что следует далее – аргументы, передаваемые программе[3]. Python сохраняет аргументы командной строки в переменной sys.argv для дальнейшего использования.

Помните, что имя запускаемого сценария[4] всегда является первым аргументом в списке sys.argv. Так что в приведённом примере 'using_sys.py' будет элементом sys.argv[0], 'we' sys.argv[1], 'are'sys.argv[2], а 'arguments' sys.argv[3]. Помните, что в Python нумерация начинается с 0, а не с 1.

sys.path содержит список имён каталогов, откуда импортируются модули. Заметьте, что первая строка в sys.path пуста; эта пустая строка показывает, что текущая директория также является частью sys.path, которая совпадает со значением переменной окружения PYTHONPATH. Это означает, что модули, расположенные в текущем каталоге, можно импортировать напрямую. В противном случае придётся поместить свой модуль в один из каталогов, перечисленных в sys.path.

Помните, что текущий каталог – это каталог, в котором была запущена программа. Выполните “import os; print(os.getcwd())”, чтобы узнать текущий каталог программы.
Файлы байткода .pyc

Импорт модуля – относительно дорогостоящее мероприятие, поэтому Python предпринимает некоторые трюки для ускорения этого процесса. Один из способов – создать байт-компилированные файлы (или байткод) с расширением .pyc, которые являются некой промежуточной формой, в которую Python переводит программу (помните раздел “Введение” о том, как работает Python?). Такой файл .pyc полезен при импорте модуля в следующий раз в другую программу – это произойдёт намного быстрее, поскольку значительная часть обработки, требуемой при импорте модуля, будет уже проделана. Этот байткод также является платформо-независимым.

Примечание: Обычно файлы .pyc создаются в том же каталоге, где расположены и соответствующие им файлы .py. Если Python не может получить доступ для записи файлов в этот каталог, файлы .pyc созданы не будут.
👍1
Оператор from ... import ...

Чтобы импортировать переменную argv прямо в программу и не писать всякий раз sys. при обращении к ней, можно воспользоваться выражением “from sys import argv”.

Для импорта всех имён, использующихся в модуле sys, можно выполнить команду “from sys import *”. Это работает для любых модулей.

В общем случае вам следует избегать использования этого оператора и использовать вместо этого оператор import, чтобы предотвратить конфликты имён и не затруднять чтение программы.

Пример:

from math import *
n = int(input("Введите диапазон:- "))
p = [2, 3]
count = 2
a = 5
while (count < n):
b=0
for i in range(2,a):
if ( i <= sqrt(a)):
if (a % i == 0):
print(a,"непростое")
b = 1
else:
pass

if (b != 1):
print(a,"простое")
p = p + [a]
count = count + 1
a = a + 2
print(p)
Имя модуля – __name__

У каждого модуля есть имя, и команды в модуле могут узнать имя их модуля. Это полезно, когда нужно знать, запущен ли модуль как самостоятельная программа или импортирован. Как уже упоминалось выше, когда модуль импортируется впервые, содержащийся в нём код исполняется. Мы можем воспользоваться этим для того, чтобы заставить модуль вести себя по-разному в зависимости от того, используется ли он сам по себе или импортируется в другую программу. Этого можно достичь с применением атрибута модуля под названием __name__.

Пример: (сохраните как using_name.py)

if __name__ == '__main__':
print('Эта программа запущена сама по себе.')
else:
print('Меня импортировали в другой модуль.')

Вывод:

$ python3 using_name.py
Эта программа запущена сама по себе.

$ python3
>>> import using_name
Меня импортировали в другой модуль.
>>>

Как это работает:

В каждом модуле Python определено его имя – __name__[5] . Если оно равно '__main__', это означает, что модуль запущен самостоятельно пользователем, и мы можем выполнить соответствующие действия.
Создание собственных модулей

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

Пример: (сохраните как mymodule.py)

def sayhi():
print('Привет! Это говорит мой модуль.')

__version__ = '0.1'

# Конец модуля mymodule.py

Выше приведён простой модуль. Как видно, в нём нет ничего особенного по сравнению с обычной программой на Python. Далее посмотрим, как использовать этот модуль в других наших программах.

Помните, что модуль должен находиться либо в том же каталоге, что и программа, в которую мы импортируем его, либо в одном из каталогов, указанных в sys.path.

Ещё один модуль (сохраните как mymodule_demo.py):

import mymodule

mymodule.sayhi()
print ('Версия', mymodule.__version__)

Вывод:

$ python mymodule_demo.py
Привет! Это говорит мой модуль.
Версия 0.1
Как это работает:

Обратите внимание, что мы используем всё то же обозначение точкой для доступа к элементам модуля. Python повсеместно использует одно и то же обозначение точкой, придавая ему таким образом характерный “Python-овый” вид и не вынуждая нас изучать всё новые и новые способы делать что-либо.

Вот версия, использующая синтаксис from..import (сохраните как mymodule_demo2.py):

from mymodule import sayhi, __version__

sayhi()
print('Версия', __version__)

Вывод: mymodule_demo2.py такой же, как и mymodule_demo.py.

Обратите внимание, что если в модуле, импортирующем данный модуль, уже было объявлено имя __version__, возникнет конфликт. Это весьма вероятно, так как объявлять версию любого модуля при помощи этого имени – общепринятая практика. Поэтому всегда рекомендуется отдавать предпочтение оператору import, хотя это и сделает вашу программу немного длиннее.

Вы могли бы также использовать:

from mymodule import *

Это импортирует все публичные имена, такие как sayhi, но не импортирует __version__, потому что оно начинается с двойного подчёркивания

Дзэн Python Одним из руководящих принципов в Python является “Явное лучше Неявного”. Выполните команду “import this”, чтобы узнать больше, а также просмотрите это обсуждение, в котором приводятся примеры по каждому из принципов.