我有以下代码来计算素数的数量,我已经在处理器的循环中划分了工作。问题是当子程序将循环的子部分分配给处理器时,它根据等级分配,我似乎无法控制它们到达的顺序
,即我希望它来为0,1,2,3 ......而不是像2,1,0,3 ..
因此,如果循环和5个处理器中有500次迭代。
等级1执行[101-200]等...
program main
implicit none
include 'mpif.h'
integer(4), parameter :: n = 36500
integer(4) :: a(n)
integer(4) :: i
integer(4) :: j
integer(4) :: ista
integer(4) :: iend
integer(4) :: sum
integer(4) :: f=0
integer(4) :: ssum
integer(4) :: ierr
integer(4) :: iproc
integer(4) :: nproc
call MPI_INIT(ierr)
call MPI_COMM_SIZE(MPI_COMM_WORLD, nproc, ierr)
call MPI_COMM_RANK(MPI_COMM_WORLD, iproc, ierr)
call loop_range(2, n, nproc, iproc, ista, iend)
sum = 0.0
print *,ista,"-",iend,">",iproc
do i = ista, iend
f=0
do j=2,INT(SQRT(REAL(i)))
if(MOD(i,j)==0) then
f=1
end if
end do
if(f==0) then
sum = sum + 1
end if
end do
call MPI_REDUCE(sum, ssum, 1, MPI_INTEGER,MPI_SUM, 0,MPI_COMM_WORLD, ierr)
if ( iproc == 0 ) write(6,*)'Total No of primes=', ssum
call MPI_FINALIZE(ierr)
end program main
subroutine para_range(n1, n2, nprocs, irank, ista, iend)
integer(4) :: n1 ! Lowest value of iteration variable
integer(4) :: n2 ! Highest value of iteration variable
integer(4) :: nprocs ! No of Cores/Processors you want to use
integer(4) :: irank ! Process rank
integer(4) :: ista ! Start of iterations for rank iproc
integer(4) :: iend ! End of iterations for rank iproc
integer(4) :: iwork1, iwork2
print *,irank
iwork1 = ( n2 - n1 + 1 ) / nprocs
iwork2 = MOD(n2 - n1 + 1, nprocs)
ista = irank * iwork1 + n1 + MIN(irank, iwork2)
iend = ista + iwork1 - 1
if ( iwork2 > irank ) then
iend = iend + 1
end if
end subroutine para_range
我正在使用Open MPI。
答案 0 :(得分:1)
这个问题与你的其他问题(Open MPI ranks are not in order)几乎相同,答案是一样的。你误解了这个问题。
在你的案件中,“排序”可以被视为任意和不重要。您分配问题的等级将执行您为其分配的工作。您遇到的问题是您希望它们按排序顺序打印出来。这在MPI中是不可能的。如果您在同一时间打印来自所有等级的消息,则无法保证以任何特定顺序打印消息。原因是所有输出必须首先发送到启动应用程序mpiexec
或mpirun
的进程,然后打印到屏幕上。对于某些进程,此传输可能比其他进程更快。如果按顺序输出所有结果至关重要,则必须先将它们全部发送到同一进程,然后从那里打印出来。保证如果您以相同的等级打印所有文本,它们将以正确的顺序出现。
所以你的代码看起来大致如下:
...initialize variables...
...divide up work...
...each work does the work assigned to it...
...MPI_SEND result to rank 0...
if (rank == 0)
MPI_RECV results from all processes
print results in order