C MPI-使用MPI_Probe()时发送我自己的结构

C MPI-使用MPI_Probe()时发送我自己的结构,c,struct,parallel-processing,mpi,C,Struct,Parallel Processing,Mpi,我需要用MPI_send()发送我自己的结构。问题是,我不知道如何正确使用MPI中的结构。当然,我试着自己去寻找,但是我没有找到任何适合我需要的例子 现在,当我运行Makefile时,出现了以下错误: probe_and_struct.c: In function ‘main’: probe_and_struct.c:72:13: error: expected ‘;’ before ‘buf’ myStruct buf; ^ probe_and_struct.

我需要用MPI_send()发送我自己的结构。问题是,我不知道如何正确使用MPI中的结构。当然,我试着自己去寻找,但是我没有找到任何适合我需要的例子

现在,当我运行Makefile时,出现了以下错误:

probe_and_struct.c: In function ‘main’:
probe_and_struct.c:72:13: error: expected ‘;’ before ‘buf’
    myStruct buf;
             ^
probe_and_struct.c:73:4: error: ‘buf’ undeclared (first use in this function)
    buf = (myStruct *) malloc( sizeof(myStruct) * status_size );
    ^
probe_and_struct.c:73:4: note: each undeclared identifier is reported only once for each function it appears in
probe_and_struct.c:73:21: error: expected expression before ‘)’ token
    buf = (myStruct *) malloc( sizeof(myStruct) * status_size );
                     ^
make: *** [probe_and_struct] Error 1
那么,你能告诉我,我做错了什么,我应该如何正确使用这个结构吗

编辑: 我已经重写了代码,但是现在程序在MPI_Send()上由于分段错误而崩溃


这是我的密码:
我的代码-第二版:
#包括
#包括
#包括
#定义ARR_LEN 2//测试数组的长度和发送的大小
int main()
{
MPI_Init(NULL,NULL);
//---------------------------------------------------------------------------------------------------------------------------------------
//创建自己的结构
//----------------------
//结构的结构:-)
typedef结构值
{
int-id;
字符c;
}价值观;
价值观;
//声明结构的各个部分
MPI_数据类型myStruct;
整数块长度[2];
MPI_Aint指数[2];
MPI_数据类型[2];
//初始化部分结构
BlockLength[0]=1;//结构的属性大小
区块长度[1]=1;
类型[0]=MPI_INT;//结构的属性的数据类型
类型[1]=MPI_字符;
MPI_地址(&value.id,&index[0]);
MPI_地址(&value.c,&index[1]);
//创建并提交新结构
MPI类型结构(2,块长度、索引、类型和myStruct);
MPI_Type_commit(&myStruct);
//---------------------------------------------------------------------------------------------------------------------------------------
//消息传递
//-----------------
value.id=0;
value.c='a';
//进程数,当前进程的ID
国际大世界;
MPI_Comm_大小(MPI_Comm_WORLD和WORLD_大小);
国际世界排名;
MPI通信等级(MPI通信世界级和世界级);
//要发送的测试数组
//int-arr[2]={10,20};
MPI_状态;
交换机(世界排名){
案例0:
printf(“Toto je处理cislo%d.\n\t”,世界排名);
MPI_Send(&value,sizeof(struct Values),myStruct,1,0,MPI_COMM_WORLD);
printf(“敖德拉诺-波兰因图”。\n”);
打破
案例1:
//识别消息的大小
MPI_探测器(0、0、MPI_通信世界和状态);
//发送的块数
int状态_大小;
MPI获取计数(状态、myStruct和状态大小);
认沽权(“b”);
//按所需大小分配缓冲区
值*buf;
buf=(值*)malloc(大小(值)*状态大小);
认沽权(“b”);
//接收和打印消息
//MPI_Recv(buf、状态大小、myStruct、0、0、MPI_COMM_WORLD、MPI_status_IGNORE);
printf(“Toto je处理cislo%d.\n\t[”,世界排名);
对于(int i=0;i
您像使用类型一样使用
myStruct
并试图实例化
buf
,但是
myStruct
MPI\u数据类型的一个实例(而不是类型)

这部分代码(其中
myStruct
声明为
MPI\u数据类型
):

与此部分冲突(您试图使用
myStruct
作为类型):


您像使用类型一样使用
myStruct
,并试图实例化
buf
,但
myStruct
MPI\u数据类型的实例(而不是类型)

这部分代码(其中
myStruct
声明为
MPI\u数据类型
):

与此部分冲突(您试图使用
myStruct
作为类型):


MPI\u类型
与变量类型混淆。例如,让我们使用一个简单的
int
int
MPI\u类型是
MPI\u int
,对吗?但这不是正确的代码:

MPI_INT a = 5; //wrong, MPI_INT is an MPI_Type
               //not the type we want to declare a variable
MPI_Send(&a, 1, MPI_INT, 1, 0, MPI_COMM_WORLD);
相反,您可以使用:

int a = 5; //int is used to declare a variable
MPI_Send(&a, 1, MPI_INT, 1, 0, MPI_COMM_WORLD); //MPI_INT is the type to 
                                                //send the variable
struct value a = {4, 'b'}; //struct value is used to declare the variable
MPI_Send(&a, 1, myStruct, 1, 0, MPI_COMM_WORLD); //myStruct is the MPI_Type used to 
                                                 //send the variable
类似地,如果您的结构为:

struct value {
    int id;
    char c;
};
然后,在使用
MPI\u Type\u commit
声明新的MPI类型后,您将使用:

int a = 5; //int is used to declare a variable
MPI_Send(&a, 1, MPI_INT, 1, 0, MPI_COMM_WORLD); //MPI_INT is the type to 
                                                //send the variable
struct value a = {4, 'b'}; //struct value is used to declare the variable
MPI_Send(&a, 1, myStruct, 1, 0, MPI_COMM_WORLD); //myStruct is the MPI_Type used to 
                                                 //send the variable

MPI\u类型
与变量类型混淆。例如,让我们使用一个简单的
int
int
MPI\u类型是
MPI\u int
,对吗?但这不是正确的代码:

MPI_INT a = 5; //wrong, MPI_INT is an MPI_Type
               //not the type we want to declare a variable
MPI_Send(&a, 1, MPI_INT, 1, 0, MPI_COMM_WORLD);
相反,您可以使用:

int a = 5; //int is used to declare a variable
MPI_Send(&a, 1, MPI_INT, 1, 0, MPI_COMM_WORLD); //MPI_INT is the type to 
                                                //send the variable
struct value a = {4, 'b'}; //struct value is used to declare the variable
MPI_Send(&a, 1, myStruct, 1, 0, MPI_COMM_WORLD); //myStruct is the MPI_Type used to 
                                                 //send the variable
类似地,如果您的结构为:

struct value {
    int id;
    char c;
};
然后,在使用
MPI\u Type\u commit
声明新的MPI类型后,您将使用:

int a = 5; //int is used to declare a variable
MPI_Send(&a, 1, MPI_INT, 1, 0, MPI_COMM_WORLD); //MPI_INT is the type to 
                                                //send the variable
struct value a = {4, 'b'}; //struct value is used to declare the variable
MPI_Send(&a, 1, myStruct, 1, 0, MPI_COMM_WORLD); //myStruct is the MPI_Type used to 
                                                 //send the variable

您没有正确构造MPI数据类型。或者更确切地说,您在发送结构时没有正确使用构造的数据类型。您应该执行以下任一操作:

1.修复数据类型内的偏移量 此代码:

// Initialize parts of structure
blockLengths[0] = 1; // stucture's attributes' sizes
blockLengths[1] = 1;
types[0] = MPI_INT; // structure's attributes' data types
types[1] = MPI_CHAR;
MPI_Address( &value.id, &indices[0] );
MPI_Address( &value.c, &indices[1] );

// Create and commit new structure
MPI_Type_struct( 2, blockLengths, indices, types, &myStruct );
MPI_Type_commit( &myStruct );

...

MPI_Send( &value, sizeof(struct Values), myStruct, 1, 0, MPI_COMM_WORLD);
应成为:

// Initialize parts of structure
blockLengths[0] = 1; // stucture's attributes' sizes
blockLengths[1] = 1;
types[0] = MPI_INT; // structure's attributes' data types
types[1] = MPI_CHAR;
MPI_Address( &value.id, &indices[0] );
MPI_Address( &value.c, &indices[1] );

// Convert the absolute addresses into offsets
indices[1] -= indices[0];
indices[0] = 0;

// Create and commit new structure
MPI_Type_struct( 2, blockLengths, indices, types, &myStruct );
MPI_Type_commit( &myStruct );

...

MPI_Send( &value, 1, myStruct, 1, 0, MPI_COMM_WORLD);
此外,如果您愿意发送这样一个数据类型的数组,您应该采取一些特殊措施来考虑编译器所做的类型填充。看看怎么做

2.发送数据时使用MPI_BOTTOM 您可以保留绝对地址,而不是固定类型描述中的偏移量。缺点是,对于绝对地址,您只能发送构建数据类型时使用的特定变量的内容(因为其他变量通常会在内存中的其他地方结束)。使用此类数据类型时,不指定缓冲区的地址,而是指定MPI_BOTTOM,即此代码:

MPI_Send( &value, sizeof(struct Values), myStruct, 1, 0, MPI_COMM_WORLD);
变成:

MPI_Send( MPI_BOTTOM, 1, myStruct, 1, 0, MPI_COMM_WORLD);
请注意,在这种情况下,要发送的元素数