Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/loops/2.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181

Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/.net/23.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
将c顺序转换为OpenMP问题_C_Loops_Openmp - Fatal编程技术网

将c顺序转换为OpenMP问题

将c顺序转换为OpenMP问题,c,loops,openmp,C,Loops,Openmp,我正在研究一个n体赋值,它使用OpenMP将顺序程序转换为并行程序。我有下面的函数,它在OpenMP关闭时可以正常工作,但在其他情况下会产生不正确的结果。我有一个锁,锁定了循环中唯一更新的变量,这些变量没有在循环中声明。我已经盯着它看了很长时间了,我不知道我做错了什么。如有任何提示,将不胜感激 void update() { int i, j; Body *tmp; omp_lock_t lock; omp_init_lock(&lock); for (i=0;

我正在研究一个n体赋值,它使用OpenMP将顺序程序转换为并行程序。我有下面的函数,它在OpenMP关闭时可以正常工作,但在其他情况下会产生不正确的结果。我有一个锁,锁定了循环中唯一更新的变量,这些变量没有在循环中声明。我已经盯着它看了很长时间了,我不知道我做错了什么。如有任何提示,将不胜感激

void update() {
  int i, j;
  Body *tmp;

  omp_lock_t lock;
  omp_init_lock(&lock);

  for (i=0; i<numBodies; i++) {
    double x = bodies[i].x;
    double y = bodies[i].y;
    double vx = bodies[i].vx;
    double vy = bodies[i].vy;
    double ax = 0;
    double ay = 0;

    #pragma omp parallel for num_threads(4)
    for (j=0; j<numBodies; j++) {
      double r, mass, dx, dy, r_squared, acceleration;

      if (j==i) continue;
      dx = bodies[j].x - x;
      dy = bodies[j].y - y;
      mass = bodies[j].mass;
      r_squared = dx*dx + dy*dy;
      if (r_squared != 0) {
        r = sqrt(r_squared);
        if (r != 0) {
          acceleration = K*mass/(r_squared);
          omp_set_lock(&lock);
          ax += acceleration*dx/r;
          ay += acceleration*dy/r;
          omp_unset_lock(&lock);
        }
      }
    }
    x += vx;
    y += vy;
    if (x>=x_max || x<x_min) x=x+(ceil((x_max-x)/univ_x)-1)*univ_x;
    if (y>=y_max || y<y_min) y=y+(ceil((y_max-y)/univ_y)-1)*univ_y;
    vx += ax;
    vy += ay;
    assert(!(isnan(x) || isnan(y)));
    assert(!(isnan(vx) || isnan(vy)));
    bodies_new[i].x = x;
    bodies_new[i].y = y;
    bodies_new[i].vx = vx;
    bodies_new[i].vy = vy;
  }
  tmp = bodies;
  bodies = bodies_new;
  bodies_new = tmp;
  omp_destroy_lock(&lock);
}
void update(){
int i,j;
机构*tmp;
omp\u锁\u t锁;
omp_init_lock(&lock);

对于(i=0;i将pragma移动到外循环,删除了reduce并将i和j添加为private)。

将pragma移动到外循环,删除reduce并将i和j添加为private。

为什么要使用锁?只需声明
reduce(+:ax,ay)
就可以了(虽然我不确定这是否能解决您的问题,因为我现在看不出除了这个以外还有什么问题)。你能提供一个显示使用OpenMP时错误的列表吗?你得到了什么?你期望得到什么?我的意思是,如何比较不正确的值和正确的值?你的串行版本看起来如何?它是否工作?它可能也是你想要的,但我必须问你是否确定要将双精度与相等/不相等进行比较?我能够解决这个问题通过将pragma移动到外部循环并声明j和I是私有的来解决此问题。很抱歉在原始帖子中不清楚,但感谢所有花时间阅读并回答此问题的人。为什么要使用锁?只需声明
reduce(+:ax,ay)
,这样应该更好(虽然我不确定这是否能解决您的问题,因为我现在看不出除了这个以外还有什么问题)。你能提供一个显示使用OpenMP时错误的列表吗?你得到了什么?你期望得到什么?我的意思是,如何比较不正确的值和正确的值?你的串行版本看起来如何?它是否工作?它可能也是你想要的,但我必须问你是否确定要将双精度与相等/不相等进行比较?我能够解决这个问题通过将pragma移到外部循环并声明j和I是私有的来解决问题。很抱歉在原始帖子中不清楚,但感谢大家花时间阅读并回复。