开发者

openmpi question

want to distribute a vector with overlapping elements. For example, i开发者_运维百科f I had [1,2,3], I'd want [1,2] to get sent to one node, and [2,3] to get sent to another.i want it for open mpi.....please help me.....


It doesn't matter if it's for OpenMPI or not; OpenMPI is just one implementation of the standard, as is MPICH2. MPI, luckily, is MPI.

So distributing a vector of data is done with the MPI_Scatter call, which sends equal-sized chunks of the vector of data to each process in the communicator. If each task may need different numbers of elements, one uses MPI_Scatterv, where you explicitly set how many elements each process gets, and where it starts in the array.

But once you're using MPI_Scatterv and specifying counts and displacements, you can can use the counts and displacements to specify overlapping pieces of data. The counts would sum up to the number of elements in the arrays plus the overlapping bits; the displacements would point to the first, overlapping, part of the array the process sees. So for instance this distributes overlapping segments of an integer array:

#include <stdio.h>
#include <stdlib.h>
#include <mpi.h>

int main(int argc, char **argv) {
    const int NELEM=15;
    int globvec[NELEM];
    int *locvec;
    int *counts, *disps;
    int size, rank, ierr;
    int start, end;


    ierr  = MPI_Init(&argc, &argv);
    ierr |= MPI_Comm_size(MPI_COMM_WORLD, &size);
    ierr |= MPI_Comm_rank(MPI_COMM_WORLD, &rank);

    if (rank==0)
        for (int i=0;i<NELEM;i++) globvec[i] = i;

    /* figure out the counts and displacements into the array. 
     * All the tasks from 1..size-1 get one extra element
     * at the end overlapping with their neighbour; the tasks
     * size-1 gets all remaining data.
     */

    counts = (int *)malloc(size*sizeof(int));
    disps  = (int *)malloc(size*sizeof(int));
    for (int i=0; i<size; i++) {
        start = (NELEM/size)*i;

        end = (start + (NELEM/size)-1)+1;
        if (i == size-1) end = NELEM-1;

        counts[i] = (end-start+1);
        disps[i] = start;
    }

    locvec = (int *)malloc(counts[rank]*sizeof(int));
    MPI_Scatterv (globvec, counts, disps, MPI_INT,
                  locvec, counts[rank], MPI_INT, 0, MPI_COMM_WORLD);


    for (int i=0; i<counts[rank]; i++)
        printf("%d: %d\n", rank, locvec[i]);

    free(locvec);
    free(counts);
    free(disps);
    MPI_Finalize();

    return 0;
}

There are 15 elements, 0..14. So if you run it with three tasks, and there's overlap of 1, you'd expect the array to be broken up [0,1,2,3,4,5],[5,6,7,8,9,10],[10,11,12,13,14,15], and that's what you get:

$ mpirun -np 3 ./vector1
0: 0
0: 1
0: 2
0: 3
0: 4
0: 5
1: 5
1: 6
1: 7
1: 8
1: 9
1: 10
2: 10
2: 11
2: 12
2: 13
2: 14


A good point to start is the MPI wiki page. You should be able to modify the hello world example to do just what you desire.

I am not really sure what your specific problem is. It would really help if you state how much you already did, and what does not work for you.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜