通过正确定义索引列表来提高代码的效率



我问了这个问题,通过重新构建if语句/do循环来避免重复代码,以确定如何提高代码的效率。这个解决方案对我帮助很大,如下所示。

function grad(psi)
implicit none
integer, parameter :: nx = 24, ny = 24, nxx = nx / 2, nyy = ny / 2
real, parameter :: pi = 4 * atan(1.0), f0 = pi ** 2 * 1.3
complex, dimension(3,3,-nx:nx,-ny:ny) :: psi, grad
grad(:,:,-nx+1:nx-1,-ny+1:ny-1) = psi(:,:,-nx+2:nx,-ny+1:ny-1)
grad(:,:,0,0) = psi(:,:,1,0)
grad(:,:,[-nxx,nxx],[-nyy,nyy,ny]) = psi(:,:,[-nxx+1,nxx+1],[-nyy,nyy,ny]) - f0 * psi(:,:,[-nxx,nxx],[-nyy,nyy,ny])
end

然而,我现在需要进一步优化我的代码。

在上面的例子中,给出了一部分

grad(:,:,[-nxx,nxx],[-nyy,nyy,ny]) = psi(:,:,[-nxx+1,nxx+1],[-nyy,nyy,ny]) - ...

它通过考虑列表CCD_ 1等的所有组合而有效地完成了我所需要的

然而,我需要的索引列表远不止[-nxx,nxx],[-nyy,nyy]。我真的需要像[-nxx,nxx,-nxx1,nxx1,-nxx2,nxx2,-nxx3,nxx3], [-nyy,nyy,-nyy1,nyy1,-nyy2,nyy2,-nyy3,nyy3]等的东西,其中nxx = nx/2, nxx1 = nx/4, nxx2 = nx/8, nxx3 = nx/16

有没有一种方法可以让我高效地做到这一点?例如,我可以只定义一个变量吗?例如:

integer : Listx, Listy
Listx = [-nxx,nxx,-nxx1,nxx1,-nxx2,nxx2,-nxx3,nxx3]
Listy = [-nyy,nyy,-nyy1,nyy1,-nyy2,nyy2,-nyy3,nyy3]

然后有类似的东西

grad(:,:,Listx,Listy) = psi(:,:,Listx+1,Listy) - ...

我确实尝试过这样做,但将Listx、Listy定义为整数似乎会带来问题。我尝试了如下:

Integer :: Listx, Listy
Listx = [-nxx,nxx,-nxx1,nxx1,-nxx2,nxx2,-nxx3,nxx3]
Listy = [-nyy,nyy,-nyy1,nyy1,-nyy2,nyy2,-nyy3,nyy3]

但在编译Fortran时,告诉我"不兼容列为0,赋值为…">

我如何才能正确定义它?感谢

如注释所述,数组声明中缺少dimension属性:

Integer :: Listx(8), Listy(8)

这应该能解决你的问题。任何导致秩为1的数组的表达式都可以作为向量下标索引器。

最新更新