c++ - MPI Allgatherv 函数出现问题

标签 c++ mpi

我一直在努力尝试并行计算这个计算粒子之间相互作用的函数。我有一个使用 Allgatherv 的想法,它应该将我的原始缓冲区分发给所有其他进程。然后使用“rank”创建一个循环,其中每个进程将计算它的部分。在这个程序中,MPI 被覆盖以显示统计信息,这就是我将其称为 mpi-> 函数的原因。不幸的是,当我运行它时,我收到以下错误。有人可以告诉我哪里出了问题吗?

Error

void calcInteraction() {
    totalInteraction = 0.0;
    int procs_number;
    int rank;
    int particle_amount = particles;

    mpi->MPI_Comm_size(MPI_COMM_WORLD,&procs_number);
    mpi->MPI_Comm_rank(MPI_COMM_WORLD,&rank);
    //long sendBuffer[particle_amount];
    //int *displs[procs_number];
    //long send_counts[procs_number+mod];
    int mod = (particle_amount%procs_number);
    int elements_per_process = particle_amount/procs_number;
    int *send_buffer = new int[particle_amount]; //data to send
    int *displs = new int[procs_number]; //displacement
    int *send_counts = new int[procs_number];

    if(rank == 0)
    {
        for(int i = 0; i < particle_amount; i++)
        {
            send_buffer[i] = i; // filling buffer with particles
        }
    }
    for (int i = 0; i < procs_number;i++)
    {
        send_counts[i] = elements_per_process; // filling buffer since it can't be empty
    }

    // calculating displacement
    displs[ 0 ] = 0;
    for ( int i = 1; i < procs_number; i++ )
        displs[ i ] = displs[ i - 1 ] + send_counts[ i - 1 ];
    int allData = displs[ procs_number - 1 ] + send_counts[ procs_number - 1 ];

    int * endBuffer = new int[allData];

    int start,end; // initializing indices

    cout<<"entering allgather"<<endl;
    mpi->MPI_Allgatherv(send_buffer,particle_amount,MPI_INT,endBuffer,send_counts,displs,MPI_INT,MPI_COMM_WORLD);
    //                   ^from      ^how many        ^send   ^receive  ^how many  ^displ ^send    ^communicator
    //                               to  send         type    buffer    receive           type
    start = rank*elements_per_process;
    cout<<"start = "<< start <<endl;
    if(rank == procs_number) //in case that particle_amount is not even
    {
        end = (rank+1)*elements_per_process + mod;
    }
    else
    {
        end = (rank+1)*elements_per_process;
    }

    cout<<"end = "<< end <<endl;
    cout << "calcInteraction" << endl;

        for (long idx = start; idx < end; idx++) {
            for (long idxB = start; idxB < end; idxB++) {
                if (idx != idxB) {
                    totalInteraction += physics->interaction(x[idx], y[idx], z[idx], age[idx], x[idxB], y[idxB],
                                                             z[idxB], age[idxB]);
                }
            }
        }



    cout << "calcInteraction - done" << endl;
}

最佳答案

您没有正确使用 MPI_Allgatherv()

I had an idea to use Allgatherv which should distribute my original buffer to all other processes.

描述表明您需要 MPI_Scatter[v]() 以便从给定的等级切分您的数组,并将这些 block 分配给所有 MPI 任务。 如果所有任务都应接收完整数组,那么 MPI_Bcast() 就是您所需要的。

无论如何,我们假设您需要全体集合。

首先,您必须确保所有任务都具有相同的 particles 值。

其次,由于您从每个 MPI 任务收集相同数量的数据,并将它们存储在连续的位置,您可以使用 MPI_Allgather() 简化您的代码。如果只有最后一个任务的数据可能少一点,那么您可以使用 MPI_Allgatherv()(但这不是您的代码当前正在执行的操作)或传输一些幻影数据,以便您可以使用简单的 (并且可能更优化)MPI_Allgather()

最后但同样重要的是,您应该发送 elements_per_process 元素(而不是 particle_amount)。这应该足以摆脱崩溃(例如 MPI_ERR_TRUNCATE)。但话虽如此,我不确定这是否会达到您需要或期望的结果。

关于c++ - MPI Allgatherv 函数出现问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/47190698/

相关文章:

c - 将简单结构传递给函数时 MPI 出现段错误

c++ - 将双端队列与 C 库一起使用

c++ - Boost tokenizer 将引用的字符串视为一个标记

c - C中的MPI。我没有收到我发送的内容

fortran - 使用 MPI-2 的 RMA 函数的 Fortran 程序中的段错误

c - 如何使用 MPI 或 OpenMP 并行化函数调用

c++ - 体系结构 x86_64 的 undefined symbol -> 体系结构 x86_64 未找到符号

c++ - 将 vector 放入 map

c++ - VS 15 社区无法创建 C++ 项目

c++ - 将 MPI 数据类型返回给 MPI Gather