Python `__init __. Py` и инициализация объектов в коде

Я прочитал документацию о файлах __ init __. Py и несколько хороших вопросов по SO, но я все еще не понимаю, как правильно его использовать.

Контекст

У меня есть код со многими пакетами и подпакетами. Я определил много классов, для некоторых из которых мне нужно создать один (и только один) экземпляр для всего пользовательского сеанса. Эти новые объекты затем используются в разных частях кода, так что каждый раз, когда я (или пользователь) обновляю данные / информацию в этих объектах, они будут использоваться во всем коде без необходимости изменять что-либо еще. Для большей ясности позвольте мне показать вам базовую схему того, о чем я говорю.

Код имеет чрезмерно упрощенную структуру, например:

root/
    __init__.py
    tools/
        __init__.py
        ... (some modules)
        aliases.py (which defines the class Aliases)
    physics/
        __init__.py
        ... (some modules)
        constants/
            ... (some modules)
            constants.py (which defines the class Ctes)
        units.py (which defines the class Units)

В коде мне нужно управлять псевдонимами, единицами измерения и константами. Я нашел способ справиться с этим - создать по одному экземпляру каждого и использовать его во всем коде. С помощью этого метода Я уверен, например, что если псевдоним добавляется во время выполнения кода, его можно использовать в любом месте кода, потому что существует только один общий экземпляр псевдонимов. Это то, что мне нужно (то же самое применимо и к единицам измерения, и к константам, кстати).

Текущее состояние

На данный момент, я считаю, что способ, которым я это делаю, не самый лучший. Действительно, я создаю экземпляр, скажем, псевдонимов, сразу после объявления класса в том же файле:

в root / tools / aliases.py

import ... (stuff

class Aliases(object):
    """The Aliases manager"""
    ...

ALIASES = Aliases()

И затем, в любом файле, который мне нужно использовать псевдоним, я использую:

в any_file.py (в любом месте кода)

from root.tools.aliases import ALIASES

ALIASES.method1() # possibly in functions or other classes
ALIASES.method2() # ... etc

А для некоторых других классов я даже используя файл __ init __. py в корне кода:

в root / __ init __. py

# CTES is the instance of Ctes() created in root/physics/constants/constants.py
from root.physics.constants.constants import CTES
CTES.add(...) # add a new constant that needs to be known

(конечно, CTES не просто хранит некоторые константы, я определяю некоторые методы для их использования, поэтому имеет смысл иметь их в этом классе, а не просто определять их как обычный Python константы в модуле)

Вопросы

Мне интересно, правильно ли я делаю это (возможно, нет). Может быть, лучше использовать файлы __ init __. Py и инициировать в нем общие экземпляры. Но разве это не приносит проблем (например, циклы зависимости или увеличение использования памяти ...)? Кроме того, как использовать созданные экземпляры в другом месте кода? Как это?:

в root / tools / __ init __. Py

import root.tools.aliases as Al
ALIASES = Al.Aliases()
# should I delete the imported module: del Al ??

, а затем в any_file.py

from root.tools import ALIASES
ALIASES.method(...)

Или все эти экземпляры лучше включить в файл (например, root / shared.py ), который я импортирую в root / __ init __. py , чтобы я был уверен, что он инициирован?

Я читал много раз, лучше сохранить __ init __. py файлы пустые (как раз сейчас в моем коде, за исключением, конечно, root / __ init __. py ). Как вы думаете?

Я немного растерялся (вы, наверное, могли видеть это по тому факту, что я не очень ясен). Любая помощь / совет более чем приветствуются. Я бы хотел избежать любых непитонических решений или решений, которые могут запутать пользователя или сделать вещи небезопасными.

5
задан BradleyDotNET 16 September 2014 в 22:36
поделиться