MPI_Allgather收到垃圾邮件

时间:2019-01-03 21:36:59

标签: fortran mpi openmpi

我有以下代码:

              real          :: s_s, d_s, s_r(size), d_r(size)
              integer       :: k, k_r(size)

              ! - size = number of processors
              ! - Do something to initialise s_s, d_s, k
              write(*,*) "SENDING >>>>"
              write(*,*) s_s, d_s
              call MPI_Allgather( s_s, 1, MPI_REAL,
 &                 s_r, 1, MPI_REAL, MPI_COMM_PGM, mpi_err)

              call MPI_Allgather( d_s, 1, MPI_REAL,
 &                 d_r, 1, MPI_REAL, MPI_COMM_PGM, mpi_err)

              call MPI_Allgather ( k, 1, MPI_INTEGER,
 &                 k_r, 1, MPI_INTEGER, MPI_COMM_PGM, mpi_err)


              write(*,*) "RECEIVED <<<<"
              write(*,*) s_r, d_r, kr

这将产生以下输出:

SENDING >>>>
  -1803.80339864908       0.616157856320407     
 RECEIVED <<<<
  6.953077622513053E-310  3.565412685916647E-314  1.221334434576037E-314
  1.498827614035474E-314  6.952991536467244E-310  6.953288052096687E-310
  6.953108563966064E-310  2.350861403096908E-314           4           1
           2           3

kr正在正确收集,但是s_r和d_r似乎正在接收垃圾。难道是因为MPI数据类型?我尝试使用MPI_REAL MPI_REAL8MPI_DOUBLE,但是没有用。此外,mpi_err = MPI_SUCCESS

该如何解决?

编辑1 我研究了以下原型程序:

program allgather
  implicit none

  include "mpif.h"

  real a(4)
  integer rank,size,ierr
  real as(4)
  real ar(16)
  integer i, j, k,z 

  a=1
  call MPI_INIT(ierr)
  call MPI_COMM_RANK(MPI_COMM_WORLD, rank, ierr)
  call MPI_COMM_SIZE(MPI_COMM_WORLD, size, ierr)
  if(size.ne.4)then 
     write(*,*)'Error!:# of processors must be equal to 4'
     write(*,*)'Programm aborting....'
     call MPI_ABORT(ierr)
  endif

  do k=1,4
     if ( rank == (mod(k, size))) then
        a(k)  = k
     else
        a(k)  = 0.0 
     endif
  enddo

  write(*,*) "Rank :", rank
  write(*,*) a

  call MPI_Allgather(a, 4, MPI_REAL, ar,
 &     4,
 &     MPI_REAL, MPI_COMM_WORLD, ierr)

  write(*,*) "Recieved array"
  write(*,*) ar

  do i = 1, 16
     if ( ar(i) /= 0.0 ) then
        z = mod(i, size)
        if ( z == 0 ) then
           a( size ) = ar(i)
        else
           a ( z ) = ar(i)
        endif
     endif
  enddo

  write(*,*) "---------"
  write(*,*) a
  write(*,*) "---------"

  call MPI_FINALIZE(ierr)
  end

这会产生预期的结果,即ar不会产生垃圾。但是,我无法说出实现之间的区别。

1 个答案:

答案 0 :(得分:2)

事实证明,对于项目,要使用的数据类型为MPI_FLT。奇怪的是MPI_FLT而不是MPI_REALx有效,其中x = 4,8也不MPI_FLOAT。我在项目中使用了MPI_FLT,以查看其定义,但未在项目中的任何地方出现。

我正在使用的OpenMPI版本是:

$ mpirun --version
mpirun (Open MPI) 3.0.0

我使用的编译器是:

$ mpifort --version
ifort (IFORT) 19.0.1.144 20181018

在以后的编辑中,我将详细说明原因。