我如何在OpenVino上进行异步推断

时间:2019-06-18 07:25:06

标签: python-multithreading openvino

我编写了一个python服务器,该服务器使用OpenVino网络对传入的请求进行推断。为了加快处理速度,我在多个线程中接收请求,并且我希望同时运行推理。 看来无论做什么,我得到的时间都与非并行解决方案相同-这使我觉得我错过了一些事情。

我正在使用openvino 2019.1.144用Python编写它。我正在对同一个插件和网络使用多个请求,以尝试使推理同时运行。

def __init__(self, num_of_requests: int = 4):
   self._plugin = IEPlugin("CPU", plugin_dirs=None)
   model_path = './Det/'
   model_xml = os.path.join(model_path, "ssh_graph.xml")
   model_bin = os.path.join(model_path, "ssh_graph.bin")
   net = IENetwork(model=model_xml, weights=model_bin)
   self._input_blob = next(iter(net.inputs))

   # Load network to the plugin
   self._exec_net = self._plugin.load(network=net, num_requests=num_of_requests)
   del net

def _async_runner(detect, images_subset, idx):
    for img in images_subset:
        request_handle = self._exec_net.start_async(request_id=idx, inputs={self._input_blob: img})
        request_handle.wait()


def run_async(images):  # These are the images to infer
    det = Detector(num_of_requests=4)
    multiplier = int(len(images)/4)
    with ThreadPoolExecutor(4) as pool:
        futures = []
        for idx in range(0,3):
            images_subset = images[idx*multiplier:(idx+1)*multiplier-1]
            futures.append(pool.submit(_async_runner, det.detect, images_subset, idx))

当我在同步模式下运行800个推论时,我得到一个平均值。 290ms的运行时间 当我以异步模式运行时,平均运行时间为280ms。 这些不是实质性的改进。我在做什么错了?

2 个答案:

答案 0 :(得分:2)

您可以参考C:\ Program Files(x86)\ IntelSWTools \ openvino_2019.1.144 \ inference_engine \ samples \ python_samples \ object_detection_demo_ssd_async \ object_detection_demo_ssd_async.py的示例代码或python_samples目录中的类似示例以检查异步方式已解决。

答案 1 :(得分:0)

如果使用wait(),执行线程将阻塞,直到结果可用为止。如果要使用真正的异步模式,则需要不阻塞执行的wait(0)。只需在需要时启动推断并存储request_id。然后,您可以检查结果是否可用,并检查wait(0)的返回值是否为0。请注意,在IE进行推理时,请不要使用相同的request_id,这将导致冲突,并且会引发冲突。

但是,在您提供的代码中,您无法执行此操作,因为您正在创建一个线程池,每个线程都将图像子集的推断执行到唯一的request_id中。实际上,这是一个并行执行,将为您带来相当不错的性能,但它不是“异步”模式。

真正的异步模式将是这样的:

while still_items_to_infer():
    get_item_to_infer()
    get_unused_request_id()
    launch_infer()
    do_someting()
    if results_available():
        get_inference_results()
        free_request_id()
        #This may be in a new thread
        process_inference_results()

这样,您可以在等待连续推理的同时分派连续推理。