Должны ли мы нарушать семантику Python для создания функций, соответствующих человеческим ментальным моделям?Python

Программы на Python
Ответить Пред. темаСлед. тема
Anonymous
 Должны ли мы нарушать семантику Python для создания функций, соответствующих человеческим ментальным моделям?

Сообщение Anonymous »

Семантика проектирования контекстного менеджера
with WorkerContext():
worker = Worker()
thread = Thread()
thread.bind(worker)
thread.start()

# Worker class' run method
class Worker:
def run(self):
# Should this code be inside WorkerContext?

В моем WorkerContext, который основан на классе AbstractContext, метод экземпляра() позволяет получить текущий экземпляр контекста даже после вызывается __exit__() контекстного менеджера. Я хочу, чтобы worker.run() мог получить доступ к экземпляру контекста через WorkerContext.instance() во время его выполнения.
Однако в соответствии с контекстом Python семантики менеджера, после вызова __exit__() считается, что менеджер контекста завершил работу, и, как правило, экземпляр больше не является действительным. Мой вопрос: должен ли я намеренно нарушать семантику контекстного менеджера Python, чтобы экземпляр контекста оставался доступным после __exit__()?
Был бы этот дизайн разумным или он мог бы ввести потенциальные проблемы?
class AbstractContext(ABC):
"""
Base class for context managers.

Notes:
TODO: Support cross-process usage.
TODO: Support cross-machine usage.
TODO: Support cross-cluster usage.
"""
_global_stack = []
_lock = threading.Lock()

@classmethod
def instance(cls: type[T]) -> Optional[T]:
with cls._lock:
if not cls._global_stack:
return None
return next((ctx for ctx in reversed(cls._global_stack) if isinstance(ctx, cls)), None)

@classmethod
def stack(cls: type[T]) -> List[T]:
with cls._lock:
return [ctx for ctx in cls._global_stack if isinstance(ctx, cls)]

Или более дружелюбный способ описать проблему: является ли ее область действия динамической или статической, хотя это описание может быть немного неправильным, я считаю, что оно вполне отражает суть проблемы.< /p>
Когда я запускаю поток в WorkContext и выполняю его, я, естественно, думаю, что он выполняется в WorkContext, который является статическим.
Но на самом деле , он просто запускает поток, а затем завершает его, при этом внутренняя работа потока на самом деле не выполняется здесь, как мы могли бы себе представить. Я действительно не знаю, как здесь спроектировать его поведение.
Примечание: я не ищу конкретного решения, а скорее хочу понять, что представляет собой элегантный подход.

Я прикрепил контент и теперь это стало так:
worker = Worker()
thread = Thread()
thread.bind(worker)
worker.inject(WorkerContext())
thread.start()

class AbstractWorker:

def __init__(self):
self._injected_contexts = []
self._stack = contextlib.ExitStack()

def inject(self, *contexts: Context): # TODO: add ContextType
self._injected_contexts.extend(contexts)

def __enter__(self):
self._stack.__enter__()
for context in self._injected_contexts:
self._stack.enter_context(context)
return self

def __exit__(self, exc_type, exc_val, exc_tb):
self._stack.__exit__(exc_type, exc_val, exc_tb)
return False


Подробнее здесь: https://stackoverflow.com/questions/790 ... n-mental-m
Реклама
Ответить Пред. темаСлед. тема

Быстрый ответ

Изменение регистра текста: 
Смайлики
:) :( :oops: :roll: :wink: :muza: :clever: :sorry: :angel: :read: *x)
Ещё смайлики…
   
К этому ответу прикреплено по крайней мере одно вложение.

Если вы не хотите добавлять вложения, оставьте поля пустыми.

Максимально разрешённый размер вложения: 15 МБ.

  • Похожие темы
    Ответы
    Просмотры
    Последнее сообщение

Вернуться в «Python»