简体   繁体   English

MPI_Scatter,散布对角线元素

[英]MPI_Scatter, to scatter a diagonal elements

I am trying to solve a simple program using the MPI Library. 我正在尝试使用MPI库解决一个简单的程序。

There is 4*N × 4*N matrix is stored on process 0. Length of each side of the matrix is DIM LEN = 4*N. 在进程0上存储有4 * N×4 * N个矩阵。矩阵每一侧的长度为DIM LEN = 4 * N。 I need to crate a diagonal Datatype. 我需要建立对角线数据类型。 However, instead of 4*N, the datatype should only cover N consecutive elements on the diagonal.Then I have to use the created datatype to distribute the diagonal of this matrix equally among processes of the MPI program. 但是,数据类型应该只覆盖对角线上的N个连续元素,而不是4 * N,然后我必须使用创建的数据类型在MPI程序的各个进程之间平均分配此矩阵的对角线。 The total number of processes is 4. 进程总数为4。

I am not able to receive the diagonal elements properly after scattering. 散布后我无法正确接收对角线元素。

Non root : 3 
Non root : 1 
2.000000 0.000000 
6.000000 0.000000 
Non root : 2 
4.000000 0.000000 

This is the program 这是程序

#include "mpi.h"
#include <stdio.h>
#define DIM_LEN 8
int main( int argc, char *argv[] )
{
int myid, numprocs;
double mat[DIM_LEN][DIM_LEN];
double matRcv[DIM_LEN/4];

int i,j;
MPI_Datatype diagonal;

MPI_Init(&argc,&argv);

MPI_Comm_size(MPI_COMM_WORLD,&numprocs);
MPI_Comm_rank(MPI_COMM_WORLD,&myid);

MPI_Type_vector(DIM_LEN/4, 1, DIM_LEN +1 , MPI_DOUBLE, &diagonal);
MPI_Type_commit(&diagonal);

  if (myid == 0){
    printf("Root : %d \n",myid); 
        for ( i=0; i<DIM_LEN; i++)
            for ( j=0; j<DIM_LEN; j++ )
                mat[i][j] = i+j;

        for ( i=0; i<DIM_LEN; i++){
           for ( j=0; j<DIM_LEN; j++ ){
                printf("%lf \t",mat[i][j] );       
           }
           printf("\n");
       }

    /* Scatter the big table to everybody's little table */
}

MPI_Scatter(&mat[0] , 1, diagonal, &matRcv ,1, diagonal, 0, MPI_COMM_WORLD);
MPI_Barrier(MPI_COMM_WORLD);

if(myid != 0){
        printf("Non root : %d \n",myid); 

         for ( i=0; i<DIM_LEN/4; i++)
                printf("%lf ",matRcv[i] );  

           printf("\n");
}

MPI_Type_free(&diagonal);
MPI_Finalize();
return 0;
}

OK. 好。 Now that you are correctly striding your diagonal datatype, your datatype should be properly reflecting the memory locations you want in your 2D array mat . 既然您正确地跨过diagonal数据类型,那么数据类型应该正确地反映了2D阵列mat所需的存储位置。 Note however, that your diagonal datatype does NOT reflect the memory locations you eventually want in your 1D arrays matRcv . 但是请注意, diagonal数据类型不会反映您最终在1D数组matRcv想要的存储位置。 The memory locations you want to receive are the DIM_LEN/4 contiguous slots of memory starting from matRcv[0] . 您要接收的内存位置是从matRcv[0]开始的DIM_LEN/4个连续内存插槽。 You can either create a 2nd datatype to describe this memory mapping (using MPI_Type_contiguous ) or more easily just call it as DIM_LEN/4 doubles . 您可以创建第二个数据类型来描述此内存映射(使用MPI_Type_contiguous ),也可以更轻松地将其称为DIM_LEN/4 doubles

Therefore, your MPI_Scatter call should look like: 因此,您的MPI_Scatter调用应如下所示:

MPI_Scatter(&mat[0], 1, diagonal, &matRcv, DIM_LEN/4, MPI_DOUBLE, 0, MPI_COMM_WORLD);

Note also that this is a blocking collective, so there is no need for a MPI_Barrier() after calling it; 还要注意,这是一个阻塞的集合,因此在调用它之后不需要MPI_Barrier() the barrier is implied. 暗示着障碍。

// Without this it would not work.
MPI_Type_create_resized(myType, 0, (DIM_LEN+1)*sizeof(int)*4, &colType);        

// So resize the userdefined datatype whenever Vector Type is used.
MPI_Type_commit(&colType);
MPI_Scatter(&matrix[0], 1, colType, receiveBuffer, DIM_LEN/4, MPI_INT, 0, MPI_COMM_WORLD);

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM