【问题标题】:Ordering of cout weird: MPI_Recv before MPI_Send?奇怪的 cout 排序:MPI_Send 之前的 MPI_Recv?
【发布时间】:2012-10-29 17:06:33
【问题描述】:

我有类似的东西:

if (rank == winner) {
    ballPos[0] = rand() % 128;
    ballPos[1] = rand() % 64;
    cout << "new ball pos: " << ballPos[0] << " " << ballPos[1] << endl;
    MPI_Send(&ballPos, 2, MPI_INT, FIELD, NEW_BALL_POS_TAG, MPI_COMM_WORLD);
} else if (rank == FIELD) {
    MPI_Recv(&ballPos, 2, MPI_INT, winner, NEW_BALL_POS_TAG, MPI_COMM_WORLD, MPI_STATUS_IGNORE);
    cout << "2 new ball pos: " << ballPos[0] << " " << ballPos[1] << endl;
}

但我在控制台中看到:

new ball pos: 28 59
2 new ball pos: 28 59

为什么cout 在接收之后打印在发送之前?

【问题讨论】:

  • 您确定先发送再接收吗?通话是否被阻塞?
  • 我看不出问题出在哪里。 rank == winner 首先是true,然后rank == FIELDtrue。这不正确吗?
  • @PeterWood,FIELD 是一个常数 0,winner 是从 1 到 5。所以它们是不同的。还是我误会了你?
  • @RedX,我认为 Send, Recv 应该被阻止。它的 ISend 和 IRecv 没有阻塞?

标签: c++ openmpi


【解决方案1】:

这是同时进行输出的两个不同进程。 MPI 实现通常为所有进程执行标准输出重定向,但它通常被缓冲以提高性能并最小化网络利用率。所有进程的输出然后被发送到mpiexec(或mpirun,或任何其他用于启动 MPI 作业的命令)并合并到其标准输出中。来自不同进程的不同块/行最终在输出中的顺序大多是随机的,因此您不能期望某个级别的消息会首先出现,除非采用某种进程同步。

还要注意,MPI 标准不保证所有等级都可以写入标准输出。标准提供了MPI_IO预定义的属性键,可以在MPI_COMM_WORLD上查询,以获得允许执行标准输出的进程的等级。现在大多数 MPI 实现对 MPI 作业中的所有进程执行输出重定向,因此对于此类属性查询返回 MPI_ANY_SOURCE,但不能保证总是如此。

【讨论】:

    猜你喜欢
    • 2011-11-11
    • 2014-11-27
    • 2016-04-22
    • 2016-09-09
    • 2017-10-25
    • 2014-04-17
    • 2011-01-24
    • 1970-01-01
    • 2018-05-29
    相关资源
    最近更新 更多