简体   繁体   English

使用线程加速上下文管理器的缓慢初始化

[英]Use threads to speed up slow initialization of context manager

I am consuming from a python2.7 module which I cannot easily change.我正在使用我无法轻易更改的 python2.7 模块。 This module has a factory for a class that is a context manager.这个模块有一个类的工厂,它是一个上下文管理器。 This works great for managing the lifetime of the object, but initializing this class involves waiting on creation of a cloud based resource and it can take many minutes to run.这对于管理对象的生命周期非常有效,但初始化此类涉及等待创建基于云的资源,并且可能需要几分钟才能运行。 Within the scope of my program I need to create two of the objects such as the following:在我的程序范围内,我需要创建两个对象,如下所示:

import immutable_module

cloud_resource_name1 = "load_ai_model"
cloud_resource_name2 = "create_input_output_model"

with immutable_module.create_remote_cloud_resource(cloud_resource_name1) as a, \
     immutable_module.create_remote_cloud_resource(cloud_resource_name2) as b: 
    result = __do_imporant_thing(a, b)

print(result)

Is there a way call these two contextmanagers concurrently using threads to speed up the load time?有没有办法使用线程同时调用这两个上下文管理器来加快加载时间?

After doing more research I found a solution, but it may not be the best answer.经过更多研究,我找到了一个解决方案,但这可能不是最好的答案。 The solution relies on calling __enter__ and __exit__ manually for the contextmanager.该解决方案依赖于为上下文管理器手动调用__enter____exit__

import immutable_module

cloud_resource_name1 = "load_ai_model"
cloud_resource_name2 = "create_input_output_model"

a_context = immutable_module.create_remote_cloud_resource(cloud_resource_name1) 
b_context = immutable_module.create_remote_cloud_resource(cloud_resource_name2)

a = None
b = None

try:
    def __set_a():
      global a
      a = a_context.__enter__()

    def __set_b():
      global b
      b = b_context.__enter__()

    a_thread = Thread(target=__set_a)
    b_thread = Thread(target=__set_b)

    a_thread.start()
    b_thread.start()

    a_thread.join()
    b_thread.join()

    result = __do_imporant_thing(a, b)

finally:
    try:
        if a is not None:
            a_context.__exit__(*sys.exc_info())
    finally:
        if b is not None:
            b_context.__exit__(*sys.exc_info())

print(result)

This is really dirty, not generic at all, and there are potential issues with exception handling, but it works.这真的很脏,根本不是通用的,并且存在异常处理的潜在问题,但它确实有效。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM