Codebra
29 января 2026 в 18:34

Урок 59. Пакеты модулей в Python

В этом уроке познакомимся с пакетами в Python и узнаем про относительное импортирование.
📝

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

Теоретический материал сохранен в исходном виде, а практические задания с автоматической проверкой вынесены в отдельные интенсивы и задания.

Полный список уроков доступен по тегу Архивный курс по Python и на странице первого урока.

📝 Кратко
  • Модули в Python могут группироваться в пакеты для создания нового пространства имен.
  • Пакеты включают атрибуты из подкаталогов и файлов модулей.
  • Для указания пути до модуля используется точечная нотация.
  • В Python 3.3 и выше можно использовать относительное импортирование для избежания неоднозначности и информативности кода.
  • Пакеты в Python необязательны, но полезны для добавления информативности и избежания неоднозначного импортирования.

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

Чтобы указать путь до модуля, будем использовать точечную нотацию. Предположим, модуль b.py находится в директории dir1 рабочей папки. Далее пример использования этого модуля:

'''  a.py  '''
import dir1.b
dir1.b.print_x() # => 10

Код самого модуля:

'''  b.py  '''
x = 10
y = [1, 2]

def print_x():
    print(x)

def print_y():
    print(y)

При импортировании пакетов в Python ниже версии 3.3, необходимо соблюдать важное требование: каждый каталог должен содержать файл __init__.py. Для примера выше, каталог dir1 должен задержать этот файл (для Python ниже 3.3).

Из-за импортирования пакетов у нас увеличилось количество символов, которые необходимо набирать на клавиатуре. Это неудобно, поэтому уместно немного отклонится от темы и научиться сокращать длинные пути до модуля при помощи оператора as.

'''  a.py  '''
import dir1.b as b1
b1.print_x() # => 10

Как видите из примера выше, достаточно дописать оператор as и задать удобное для вас новое имя, которое можно использовать вместо длинного пути. Или использовать оператор from:

'''  a.py  '''
from dir1 import b
b.print_x() # => 10

Вернемся к основной теме урока.

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

Необходимость использования пакетов возникнет, когда вы будете разрабатывать несколько программ на своем компьютере и, вероятно, использовать в разных проектах модули с одинаковыми именами. Пока модули с одинаковыми именами в разных каталогах, все нормально (так как Python сначала ищет в локальном каталоге, как мы выяснили в уроке «Урок 58. Написание модулей в Python»). Но что, если вы хотите использовать необходимый код из каждого файла модуля? Вам нужно будет установить новые пути поиска, что приведет к импортированию только первого найденного питоном модуля, а другой окажется «вне зоны видимости». В таких ситуациях спасают пакеты Python.

Относительное импортирование

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

'''  b.py  '''
from . import c
…

Пример выше означает, что мы импортируем модуль c.py, расположенный в том же пакете, что и модуль b.py. Помимо информативности, такой способ импортирования так же позволяет избавиться от неоднозначности.

С выходом Python 3.3 стали возможны четыре способа (модели) импортирования. Три модули вы уже видели (стандартное импортирование модулей, пакетов и относительное импортирование). В Python 3.3 и более поздних версиях можно охватывать сразу несколько каталогов, т.е. объединить несколько пакетов в одно пространство имен и не использовать файл __init__.py, о котором говорилось ранее.

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

📝

Переходите к следующему уроку курса, а так же не забудьте посмотреть новый материал на Codebra по тегу Python.