Может ли openMP использоваться как многопроцессорная обработка? - PullRequest
0 голосов
/ 29 августа 2018

У меня есть проблема, которая тривиально распараллеливается: мне нужно выполнить ту же операцию с 24 объектами cdef. Я знаю, что мог бы использовать многопроцессорность для этого, но копирование данных / запуск нового процесса занимает столько же времени, сколько и последовательное выполнение вычислений, поэтому ничего не получается. Поэтому openMP может быть лучшей альтернативой.

Операция, которую я хотел бы сделать, выглядела бы так с многопроцессорной обработкой:

multiprocess.map(f, list_of_cython_objects)

Может ли что-то вроде ниже работать? Почему, почему нет? Я понимаю, что мне нужно создать массив указателей на объекты Cython, я не могу использовать списки.

from cython.parallel import prange, threadid

with nogil, parallel():

    for i in prange(len(list_of_cython_objects), schedule='guided'):
        f(list_of_cython_objects[i])

1 Ответ

0 голосов
/ 02 сентября 2018

При условии, что большая часть f может быть выполнена без GIL (то есть он использует cdef атрибуты cdef class), тогда это может быть сделано для хорошей работы. Единственный бит, который нуждается в GIL, - это индексирование списка, и вы можете легко поместить его в блок with gil.

Иллюстративный пример:

from cython.parallel import prange, parallel

cdef class C:
    cdef double x

    def __init__(self,x):
        self.x = x

cdef void f(C c) nogil:
    c.x *= 2


def test_function():
    list_of_cython_objects = [ C(x) for x in range(20) ]
    cdef int l = len(list_of_cython_objects)
    cdef int i
    cdef C c
    with nogil, parallel():
        for i in prange(l, schedule='guided'):
            with gil:
                c = list_of_cython_objects[i]
            f(c)

Пока блоки with gil малы (с точки зрения пропорции времени вычислений), вы должны получить большую часть ожидаемого ускорения распараллеливания.

...