我开始学习MPI,并从Russian IT blog Habrahabr获得了本教程代码示例:
TableEntity.Flatten/ConvertBack
我的问题是他们为什么需要
#include <mpi.h>
#include <iostream>
#include <windows.h>
using namespace std;
double Fact(int n)
{
if (n==0) return 1;
else return n*Fact(n-1);
}
int main(int argc, char *argv[])
{
int n;
int myid;
int numprocs;
int i;
int rc;
long double drob,drobSum=0,Result, sum;
double startwtime = 0.0;
double endwtime;
n = atoi(argv[1]);
if (rc= MPI_Init(&argc, &argv)) {
cout << "Launch error" << endl;
MPI_Abort(MPI_COMM_WORLD, rc);
}
MPI_Comm_size(MPI_COMM_WORLD,&numprocs);
MPI_Comm_rank(MPI_COMM_WORLD,&myid);
if (myid == 0) {
startwtime = MPI_Wtime();
}
MPI_Bcast(&n, 1, MPI_INT, 0, MPI_COMM_WORLD);
for (i = myid; i <= n; i += numprocs)
{
drob = 1/Fact(i);
drobSum += drob;
}
MPI_Reduce(&drobSum, &Result, 1, MPI_LONG_DOUBLE, MPI_SUM, 0, MPI_COMM_WORLD);
cout.precision(20);
if (myid == 0)
{
cout << Result << endl;
endwtime = MPI_Wtime();
cout << (endwtime-startwtime)*1000 << endl;
}
MPI_Finalize();
return 0;
}
如果在所有进程中都使用{p>设置了MPI_Bcast(&n, 1, MPI_INT, 0, MPI_COMM_WORLD);
值,则
n
反正。
这是一个错误还是有任何目的?我测试了代码,没有它就可以正常工作。
我认为广播可能意味着一些过程工作流程障碍,用于正确的计算时间度量或其他目的。
我还认为可能是因为n = atoi(argv[1]);
初始化在n
调用之前进行。
如果我将MPI_Init()
放在MPI_Bcast()
之后,我是否需要这段代码中的n = atoi(argv[1]);
?
答案 0 :(得分:1)
MPI_Init()
之前的任何内容都是undefined behavior in MPI。如果您不想广播命令行参数,则应在argv
之后使用argc
和MPI_Init(&argc, &argv)
,因为这样可以保证它们可用于所有任务。
代码可以正常工作,因为许多MPI实现在初始化之前使argv
和argc
可用,但是您不应依赖此行为。