我正在尝试使用OpenMP并行化我的程序中的重力计算。距离(R和R2)的计算没有问题,但是力/加速度(A)出错了。我知道它与总和中的竞争条件有关。我已经用原子和关键结构进行了一些实验但是找不到解决方案。另外,我不确定哪些变量应该是私有的,为什么。
在使用OpenMP方面有更多经验的人是否有关于如何在以下代码示例中更正此问题的建议?
A = 0.0
!$omp parallel do
do i = 1, Nobj
do j = i + 1, Nobj
R2(i,j) = (X(j,1) - X(i,1))**2 &
+ (X(j,2) - X(i,2))**2 &
+ (X(j,3) - X(i,3))**2
R(i,j) = sqrt(R2(i,j))
do k = 1, 3
A(i,k) = A(i,k) + ((mass_2_acc(i,j) / R2(i,j)) * ((X(j,k) - X(i,k)) / R(i,j)))
A(j,k) = A(j,k) + ((mass_2_acc(i,j) / R2(i,j)) * ((X(i,k) - X(j,k)) / R(i,j)))
enddo
enddo
A(i,:) = A(i,:) * G / mass_acc(i)
enddo
!$omp end parallel do
答案 0 :(得分:3)
您正在修改A(j,k)
- j
和k
都不是"本地"线程并行索引为i
的线程。我的意思是这些索引范围都不限于特定的线程,所有线程都会更新所有A(j,k)
因此竞争条件。
您可以做的事情 - 分开R
和A
计算或不使用对称来更新A
。
此外,Fortran是专栏专业,您首先遍历外部索引,这对性能不利。