2014-01-31 64 views
0

我想通過mpi4py在一些處理器中分割大量的單個任務。 下面的例子可能說明我的意圖:使用mpi4py分割x個任務(x >> n)使用mpi4py

from mpi4py import MPI 
import numpy 
from numpy import random 

comm=MPI.COMM_WORLD 
rank=comm.Get_rank() 
size=comm.Get_size() 

def doSomething(x): 
     return numpy.sum(x) 

if rank==0: 
     v=random.random((3,3)) 
     print 'thats v_random:\n', v 

     for i in range(len(v)): 
       comm.send(v[i],dest=i) 

data=comm.recv(source=0) 
print 'my rank is {0} and my output is {1}\n'.format(rank,doSomething(data)) 

至於我與LEN執行它(五)==特效的數量,一切都很好。 但是例如當v = random.random((100,3))時,它顯然不起作用。這通常如何完成?

在此先感謝。

回答

0

我在使用Fortran的博士期間編寫了一些MPI代碼來模擬粒子軌跡,我們只是欺騙了一點點,並始終將模擬中的粒子數量設置爲2的冪,以便它們可以平均分配到處理器中。

0

好的,我找到了一些解決辦法。林肯定它不是最優雅的方式,但我真的不知道如何以另一種方式完成它。所以,如果有人遇到同樣的問題,這裏有一個醜陋的工作解決方案:

from mpi4py import MPI 
import numpy 
from numpy import random 

comm=MPI.COMM_WORLD 
rank=comm.Get_rank() 
size=comm.Get_size() 

if(rank==0): 
    v=random.random((7,3)) 
    if size>=len(v): 
     size=len(v) 
    slice_size=int(numpy.ceil(float(len(v))/float(size))) 
    slice_for_last_node=len(v)-(size-1)*slice_size  
    #xtra_slices=len(v)%size 

    rows=len(v) 
    print "slice_size:",slice_size 
    print "slice_for_last_node:",slice_for_last_node 
else: 
    slice_size=slice_for_last_node=rows=None 

size=comm.bcast(size,root=0) 
slice_size=comm.bcast(slice_size,root=0) 
slice_for_last_node=comm.bcast(slice_for_last_node,root=0) 
rows=comm.bcast(rows,root=0) 

def doSomething(x): 
     return numpy.sum(x) 

if rank==0: 

     print 'thats v_random:\n', v 

    count=1 
    cur_dest=0 

     for i in range(len(v)): 
     if(count>slice_size and cur_dest<size-1): 
      cur_dest+=1 
      count=1 
     if(cur_dest>=size-1): 
      cur_dest=size-1 

      comm.send(v[i],dest=cur_dest) 
     count+=1 

if rank<size-1: 
    count=1 
    while count<=slice_size: #slices per proc 
     data=comm.recv(source=0) 
     count+=1 
     print 'my rank is {0} and my output is {1}\n'.format(rank,doSomething(data)) 


elif rank==size-1: 
    count=1 
     while count<=slice_for_last_node: 
      data=comm.recv(source=0) 
       count+=1 
       print 'my rank is {0} and my output is {1}\n'.format(rank,doSomething(data))