如何将 MPI_BCast 与自己的数据类型对象的动态数组一起使用
How to use MPI_BCast with dynamic array of own datatype objects
通过 MPI_BCast(...)
传递动态对象指针数组时出现问题。当我尝试发送数组时出现错误 ended prematurely and may have crashed. exit code 0xc0000005
。如果我将 MPI_BCast(...)
与一个对象一起使用(例如 MPI_Bcast(myObjArray[0], dataTypeMyObject, 1, 0, MPI_COMM_WORLD);
),它会正常工作。我需要在我的实现中更改什么才能发送整个数组?
这是我的 类
的代码
class Vector3 final
{
public:
double x;
double y;
double z;
//...(methods)
}
class MyObject final
{
public:
Vector3 Force;
Vector3 Speed;
//...(methods)
};
这里是数据类型init的代码
MPI_Comm_rank(MPI_COMM_WORLD, &rank);
MPI_Datatype dataTypeVec3;
int lenVec3[3] = { 1, 1, 1 };
MPI_Aint posVec3[3] = { offsetof(class Vector3, x),offsetof(class Vector3, y), offsetof(class Vector3, z) };
MPI_Datatype typVec3[3] = { MPI_DOUBLE,MPI_DOUBLE,MPI_DOUBLE };
MPI_Type_create_struct(3, lenVec3, posVec3, typVec3, &dataTypeVec3);
MPI_Type_commit(&dataTypeVec3);
MPI_Datatype dataTypeMyObject;
int lenMyObject[2] = { 1, 1 };
MPI_Aint posMyObject[2] = { offsetof(class MyObject, Force),offsetof(class MyObject, Speed)};
MPI_Datatype typMyObject[2] = { dataTypeVec3, dataTypeVec3};
MPI_Type_create_struct(2, lenMyObject, posMyObject, typMyObject, &dataTypeMyObject);
MPI_Type_commit(&dataTypeMyObject);
这是代码的一部分 MPI_BCast(...)
MyObject** myObjArray = new MyObject * [10];
for (int i = 0; i < 10; ++i)
{
myobjArray[i] = new MyObject();
}
if(rank == 0)
myObjArray[0]->Speed = {5, 0, 0};
MPI_Bcast(myObjArray, 10, dataTypeMyObject, 0, MPI_COMM_WORLD); // Problem is here
if(rank != 0)
std::cout << "rank = "<< rank << " and speed.x = " << myObjArray[0].Speed.x << std::endl;
MPI_Bcast()
期望输入元素在内存中是连续的,即 10 个 MyObject
实例在内存中位于“彼此后面”。但在您的情况下,您将一个指针数组传递给 MPI_Bcast()
,但 MPI_Bcast()
不会取消引用各个指针。
相反,尝试
MyObject * myObjArray = new MyObject[10];
// ... initialize objects on rank 0
MPI_Bcast(myObjArray, 10, dataTypeMyObject, 0, MPI_COMM_WORLD);
通过 MPI_BCast(...)
传递动态对象指针数组时出现问题。当我尝试发送数组时出现错误 ended prematurely and may have crashed. exit code 0xc0000005
。如果我将 MPI_BCast(...)
与一个对象一起使用(例如 MPI_Bcast(myObjArray[0], dataTypeMyObject, 1, 0, MPI_COMM_WORLD);
),它会正常工作。我需要在我的实现中更改什么才能发送整个数组?
这是我的 类
class Vector3 final
{
public:
double x;
double y;
double z;
//...(methods)
}
class MyObject final
{
public:
Vector3 Force;
Vector3 Speed;
//...(methods)
};
这里是数据类型init的代码
MPI_Comm_rank(MPI_COMM_WORLD, &rank);
MPI_Datatype dataTypeVec3;
int lenVec3[3] = { 1, 1, 1 };
MPI_Aint posVec3[3] = { offsetof(class Vector3, x),offsetof(class Vector3, y), offsetof(class Vector3, z) };
MPI_Datatype typVec3[3] = { MPI_DOUBLE,MPI_DOUBLE,MPI_DOUBLE };
MPI_Type_create_struct(3, lenVec3, posVec3, typVec3, &dataTypeVec3);
MPI_Type_commit(&dataTypeVec3);
MPI_Datatype dataTypeMyObject;
int lenMyObject[2] = { 1, 1 };
MPI_Aint posMyObject[2] = { offsetof(class MyObject, Force),offsetof(class MyObject, Speed)};
MPI_Datatype typMyObject[2] = { dataTypeVec3, dataTypeVec3};
MPI_Type_create_struct(2, lenMyObject, posMyObject, typMyObject, &dataTypeMyObject);
MPI_Type_commit(&dataTypeMyObject);
这是代码的一部分 MPI_BCast(...)
MyObject** myObjArray = new MyObject * [10];
for (int i = 0; i < 10; ++i)
{
myobjArray[i] = new MyObject();
}
if(rank == 0)
myObjArray[0]->Speed = {5, 0, 0};
MPI_Bcast(myObjArray, 10, dataTypeMyObject, 0, MPI_COMM_WORLD); // Problem is here
if(rank != 0)
std::cout << "rank = "<< rank << " and speed.x = " << myObjArray[0].Speed.x << std::endl;
MPI_Bcast()
期望输入元素在内存中是连续的,即 10 个 MyObject
实例在内存中位于“彼此后面”。但在您的情况下,您将一个指针数组传递给 MPI_Bcast()
,但 MPI_Bcast()
不会取消引用各个指针。
相反,尝试
MyObject * myObjArray = new MyObject[10];
// ... initialize objects on rank 0
MPI_Bcast(myObjArray, 10, dataTypeMyObject, 0, MPI_COMM_WORLD);