2012-10-16 101 views
1

我很難弄清楚如何在c中使用OpenMPI打破循環。OpenMPI突破循環

這裏是我的循環

for(i=1; i<=steps;i++) { 

    do_calculation(psi,new_psi,&mydiff,i1,i2,j1,j2); 

    if (breakNow == 1) { 
     break; 
    } 

    diff = find_difference(); 
    if(myid == mpi_master && i % iout == 0){ 
     printf("%8d %15.5f\n",i,diff); 


     if (diff == 0.00) { 
     printf("DONE!"); 

     breakNow = 1; 

     MPI_Bcast(&breakNow, 1, MPI_INT, mpi_master, MPI_COMM_WORLD); 
     }   
    } 
    } 

我需要打破所有處理器的出循環時,有0.00的差異,但好像breakNow變量沒有被廣播到所有的處理器。我錯過了什麼嗎?

回答

0

MPI_Bcast是一個集體操作。您需要在所有進程中調用它才能完成。在等級匹配mpi_root的過程中,廣播將表現得像一個發送操作,而在所有其他等級中,它將表現爲接收操作。

只需在條件之外移動電話MPI_Bcast即可。可能是正確的地方就在if (breakNow == 1) break;行之前。

另外一個建議:如果find_difference中的所有進程返回相同的值,你可以做類似的東西:

for (i = 1; i <= steps; i++) { 

    do_calculation(psi, new_psi, &mydiff, i1, i2, j1, j2); 

    diff = find_difference(); 
    if (i % iout == 0) { 
     if (myid == mpi_master) { 
      printf("%8d %15.5f\n", i, diff); 
      if (diff == 0.00) 
      printf("DONE!"); 
     } 
     if (diff == 0.00) break; 
    } 
} 

如果find_difference只給出了主進程有意義的結果,然後修改如下:

for (i = 1; i <= steps; i++) { 

    do_calculation(psi, new_psi, &mydiff, i1, i2, j1, j2); 

    diff = find_difference(); 
    if (i % iout == 0) { 
     if (myid == mpi_master) { 
      printf("%8d %15.5f\n", i, diff); 
      if (diff == 0.00) 
      printf("DONE!"); 
     } 
     MPI_Bcast(&diff, 1, MPI_DOUBLE, mpi_master, MPI_COMM_WORLD); 
     if (diff == 0.00) break; 
    } 
} 

(我假設diffdouble類型和保存你的代碼的原始語義檢查零DIF每iout步驟一次)