Pointers 使用fftw3 mpi和现代fortran的变量转换输出:堆损坏?舍入误差?
我是现代Fortran的新手,正在尝试使用FFTW3和mpi编写一个带有转置输出的冗长程序。在调试我的爆炸程序的过程中,我注意到转换的输出在程序的一次执行到下一次执行时略有不同。我写了一个小测试程序,在我的平台上复制了这个变化,它出现在下面。64x64或128x128阵列不会出现此问题,但512x512阵列会出现此问题。这种变化似乎出现在最后几位,并不是每次都发生。我必须反复运行程序才能看到它。这是否意味着堆损坏?我找不到valgrind的任何东西。我搜索了stackoverflow并在谷歌上搜索了一下,但找不出问题所在。我是否错误地使用了指针?这只是四舍五入的错误吗 我使用默认的双精度从源代码编译fftw3 我正在使用mpifort-o fickledigits fickledigits.F90-L/usr/local/lib/openmpi-lfftw3\u mpi-lfftw3-lm编译下面的程序Pointers 使用fftw3 mpi和现代fortran的变量转换输出:堆损坏?舍入误差?,pointers,fortran,mpi,fftw,heap-corruption,Pointers,Fortran,Mpi,Fftw,Heap Corruption,我是现代Fortran的新手,正在尝试使用FFTW3和mpi编写一个带有转置输出的冗长程序。在调试我的爆炸程序的过程中,我注意到转换的输出在程序的一次执行到下一次执行时略有不同。我写了一个小测试程序,在我的平台上复制了这个变化,它出现在下面。64x64或128x128阵列不会出现此问题,但512x512阵列会出现此问题。这种变化似乎出现在最后几位,并不是每次都发生。我必须反复运行程序才能看到它。这是否意味着堆损坏?我找不到valgrind的任何东西。我搜索了stackoverflow并在谷歌上搜
仅比较一个进程运行时,输出是否有所不同?同样,使用智慧的结果是否相同?我这样问是因为计划每次可能会给出两个稍有不同的计划,这可能会导致MPI中的舍入不同。您必须显示输出,并告知您期望的输出。按照前面的注释,从单进程运行开始。到底是什么让你使用标签?告诉我们你的信息。谢谢你的回复。我还没有用智慧检查结果。我做了一系列的单进程运行,没有看到任何变化。对于多个进程,相对误差为~10^{-17}。绝对差异取决于所讨论的数字-最后3-4位数字会受到影响。我使用标记堆损坏,因为我的长程序中随机出现了垃圾,而不是上面显示的程序,并猜测内存正在损坏。我不知道哪里出了问题,我想把上述变异排除在病理学的范围之外,这就是我问这个问题的原因。原来我没有正确分配数组:切换到不合适的变换,并使用调用c_f_指针数据分配大小为2*LL的实际数组,其中LL=L/2+1,[2*LL,local_M]解决了较长程序中的问题。我显然错配了我真正的阵列。
program fickledigits
use, intrinsic :: iso_c_binding
use mpi
implicit none
include 'fftw3-mpi.f03'
!--------------------------------------------------------------------
integer(kind=4) :: np,id,ierr
integer(kind=4) :: i,j,it
integer(C_INTPTR_T), parameter :: L=512,M=L,LL=L/2+1
integer(C_INTPTR_T) :: alloc_local,local_LL,local_M
integer(C_INTPTR_T) :: local_kj_offset,local_i_offset
real(C_DOUBLE), pointer :: in(:,:)
complex(C_DOUBLE_COMPLEX), pointer :: out(:,:)
type(C_PTR) :: data,plan_r2c,plan_c2r
complex(C_DOUBLE_COMPLEX), target, allocatable :: qq(:,:)
!--------------------------------------------------------------------
call MPI_Init ( ierr )
call MPI_Comm_size ( MPI_COMM_WORLD, np, ierr )
call MPI_Comm_rank ( MPI_COMM_WORLD, id, ierr )
call fftw_mpi_init()
alloc_local = fftw_mpi_local_size_2d_transposed(LL,M,MPI_COMM_WORLD,&
local_LL,local_kj_offset,local_M,local_i_offset)
data = fftw_alloc_complex(alloc_local)
call c_f_pointer(data,out,[M,local_LL])
call c_f_pointer(data,in,[2*LL,local_M])
plan_r2c = fftw_mpi_plan_dft_r2c_2d(L,M,in,out,MPI_COMM_WORLD,&
ior(FFTW_MEASURE,FFTW_MPI_TRANSPOSED_OUT))
plan_c2r = fftw_mpi_plan_dft_c2r_2d(L,M,out,in,MPI_COMM_WORLD,&
ior(FFTW_MEASURE,FFTW_MPI_TRANSPOSED_IN))
allocate(qq(M,local_LL))
do i=1,local_LL
do j=1,M
qq(j,i)=dcmplx(j,i)
enddo
enddo
out=>qq
call fftw_mpi_execute_dft_c2r(plan_c2r,out,in)
print*, 'in(10,10)=', in(10,10)
call fftw_destroy_plan(plan_r2c)
call fftw_destroy_plan(plan_c2r)
call fftw_free(data)
deallocate(qq)
call MPI_FINALIZE(ierr)
end program