5

Я должен создать и заполнить огромные (, например, 96 Go, 72000 строк * 72000 столбцов) массив с поплавками в каждом случае, который исходит из математических формул. Массив будет вычисляться после.Самый быстрый способ создания и заполнения огромного двумерного массива?

import itertools, operator, time, copy, os, sys 
import numpy 
from multiprocessing import Pool 


def f2(x): # more complex mathematical formulas that change according to values in *i* and *x* 
    temp=[] 
    for i in combine: 
     temp.append(0.2*x[1]*i[1]/64.23) 
    return temp 

def combinations_with_replacement_counts(n, r): #provide all combinations of r balls in n boxes 
    size = n + r - 1 
    for indices in itertools.combinations(range(size), n-1): 
     starts = [0] + [index+1 for index in indices] 
     stops = indices + (size,) 
     yield tuple(map(operator.sub, stops, starts)) 

global combine 
combine = list(combinations_with_replacement_counts(3, 60)) #here putted 60 but need 350 instead 
print len(combine) 
if __name__ == '__main__': 
    t1=time.time() 
    pool = Pool()    # start worker processes 
    results = [pool.apply_async(f2, (x,)) for x in combine] 
    roots = [r.get() for r in results] 
    print roots [0:3] 
    pool.close() 
    pool.join() 
    print time.time()-t1 
  • Какой самый быстрый способ создать и заполнить такой огромный Numpy массив? Заполнение списков, затем агрегирование, а затем преобразование в массив numpy?
  • Можем ли мы распараллеливать вычисления, зная, что случаи/столбцы/строки для 2d-массива независимы для ускорения заполнения массива? Подсказки/маршруты для оптимизации таких вычислений с использованием Multiprocessing?
+0

Должен ли он быть в режиме реального времени или вы можете вычислить его офф-лайн и использовать, например мариновать, чтобы читать? –

+0

Я предпочитаю быть в режиме реального времени, но если травление быстрее, я не против ... надеюсь, что я хорошо понял ваш вопрос? – sol

ответ

0

Вы можете создать пустой массив numpy.memmap с нужной формой, а затем использовать multiprocessing.Pool для заполнения его значений. Правильное выполнение этого вопроса также обеспечило бы относительно небольшой размер памяти каждого процесса в вашем пуле.

+0

См. Http://stackoverflow.com/questions/9964809/numpy-vs-multiprocessing-and-mmap, поэтому я не думаю, что это работает –

+0

@sega_sai интересно. Я не собираюсь удалять свой ответ, потому что считаю, что другие могут научиться (как и я) видеть его вместе с вашим комментарием. Благодарю. – shx2

1

Я знаю, что вы можете создавать общие массивы numpy, которые могут быть изменены из разных потоков (при условии, что измененные области не перекрываются). Вот эскиз кода, который вы можете использовать, чтобы сделать это (я видел оригинальную идею где-то на StackOverflow, редактировать: здесь https://stackoverflow.com/a/5550156/1269140)

import multiprocessing as mp ,numpy as np, ctypes 

def shared_zeros(n1, n2): 
    # create a 2D numpy array which can be then changed in different threads 
    shared_array_base = mp.Array(ctypes.c_double, n1 * n2) 
    shared_array = np.ctypeslib.as_array(shared_array_base.get_obj()) 
    shared_array = shared_array.reshape(n1, n2) 
    return shared_array 

class singleton: 
    arr = None 

def dosomething(i): 
    # do something with singleton.arr 
    singleton.arr[i,:] = i 
    return i 

def main(): 
    singleton.arr=shared_zeros(1000,1000) 
    pool = mp.Pool(16) 
    pool.map(dosomething, range(1000)) 

if __name__=='__main__': 
    main() 
+0

Это работает? Я не понимаю интерес/трюк одиночного класса. У меня есть TypeError: объект «NoneType» не поддерживает назначение элемента. Я пробовал модификации без каких-либо результатов. Не могли бы вы мне помочь? – sol

+0

Мой код действительно работает на linux (проверен). Если у вас есть окна, я боюсь, что вы поступили иначе. (поскольку значение singleton.arr не будет наследоваться процессами из пула). –

Смежные вопросы