Python многопроцессорная обработка с нестабильными результатами - PullRequest
0 голосов
/ 16 апреля 2020

Может кто-нибудь помочь мне понять, почему этот простой пример попытки ускорить a для l oop с помощью модуля python multiprocessing дает нестабильные результаты? Я использую Manager.List для хранения значений дочерних процессов.

Очевидно, что я делаю хотя бы одну вещь неправильно. Каков будет правильный способ сделать это?

import numpy as np
import multiprocessing
from matplotlib import pyplot as plt

from functools import partial
from multiprocessing import Manager


def run_parallel(x_val, result):

    val = np.arctan(x_val)

    result.append(val)


def my_func(x_array, parallel=False):

    if not parallel:
        result = []
        for k in x_array:
            result.append(np.arctan(k))

        return result

    else:
        manager = Manager()
        m_result = manager.list()

        pool = multiprocessing.Pool(4)
        pool.map(partial(run_parallel, result=m_result), x_array)

        return list(m_result)


test_x = np.linspace(0.1,1,50)
serial = my_func(test_x,parallel=False)
parallel = my_func(test_x,parallel=True)

plt.figure()
plt.plot(test_x, serial, label='serial')
plt.plot(test_x,parallel, label='parallel')
plt.legend(loc='best')
plt.show()

Вывод, который я получаю, выглядит следующим образом

this

и каждый раз это выглядит иначе.

1 Ответ

0 голосов
/ 16 апреля 2020

Я добавил несколько функций печати, и оказалось, что порядок элементов из x_array произвольный ... Вот почему это выглядит так странно. Я думаю, вы должны сохранить аргумент и значение пар arctan, а затем упорядочить его по значению аргумента

РЕДАКТИРОВАТЬ

Я прочитал больше, и оказалось, что map возвращает значений по порядку ... Это работает так, как вы хотели:

import numpy as np
import multiprocessing
from matplotlib import pyplot as plt

from functools import partial
from multiprocessing import Manager


def run_parallel(x_val, result):

    val = np.arctan(x_val)
    return val


def my_func(x_array, parallel=False):
    if not parallel:
        result = []
        for k in x_array:
            result.append(np.arctan(k))

        return result

    else:
        manager = Manager()
        m_result = manager.list()

        pool = multiprocessing.Pool(4)
        x = pool.map(partial(run_parallel, result=m_result), x_array)
        return list(x)


test_x = np.linspace(0.1,1,50)
parallel = my_func(test_x,parallel=True)

plt.figure()
plt.plot(test_x,parallel, label='parallel')
plt.legend(loc='best')
plt.show()
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...