如何用mpi4py收集不等长数组

2024-10-02 14:27:42 发布

您现在位置:Python中文网/ 问答频道 /正文

期望行为:

我尝试在不同的节点上获取不同长度的列表,将它们收集在一个节点中,然后让主节点将它们放在一个集合中。此列表在每个节点中命名为rout_array。请注意,rout_array中的元素只是整数,在节点之间不是唯一的。在

错误:

Traceback (most recent call last):
  File "prout.py", line 160, in <module>
    main()
  File "prout.py", line 153, in main
    num = DetermineRoutingNumber(steps, goal, vertexSetSize)
  File "prout.py", line 129, in DetermineRoutingNumber
    comm.Gather(send_buffer, recv_buffer, root = 0)

  File "MPI\Comm.pyx", line 589, in mpi4py.MPI.Comm.Gather (c:\projects\mpi4py\src\mpi4py.MPI.c:97806)
  File "MPI\msgbuffer.pxi", line 525, in mpi4py.MPI._p_msg_cco.for_gather (c:\projects\mpi4py\src\mpi4py.MPI.c:34678)
  File "MPI\msgbuffer.pxi", line 446, in mpi4py.MPI._p_msg_cco.for_cco_send (c:\projects\mpi4py\src\mpi4py.MPI.c:33938)
  File "MPI\msgbuffer.pxi", line 148, in mpi4py.MPI.message_simple (c:\projects\mpi4py\src\mpi4py.MPI.c:30349)
  File "MPI\msgbuffer.pxi", line 93, in mpi4py.MPI.message_basic (c:\projects\mpi4py\src\mpi4py.MPI.c:29448)

  KeyError: 'O'

我不知道当我的代码中没有字符串时,'O'怎么会出现KeyError。所有列表都包含整数,numpy数组包含整数,这里唯一活动的字典只包含键的整数。需要注意的是,每个节点都会输出此错误。在

代码:

^{pr2}$

测试用例:

EdgesQ2.txt:

注意本例中的maxMatching = 2和{}。输出应该是3。在

0,1
1,2
2,3
0,3

EdgesQ3.txt文件:

注意本例中的maxMatching = 4和{}。输出应该是4。在

0,1
0,3
0,4
1,2
1,5
2,3
2,6
3,7
4,5
4,7
5,6
6,7

Tags: inpysrc列表节点linempi4py整数
1条回答
网友
1楼 · 发布于 2024-10-02 14:27:42

如果不同进程的长度不同,则需要使用向量变量Gatherv。提供一个包含不同长度的函数。在

不幸的是,mpi4py文档目前没有描述如何使用Gatherv或任何其他向量变体。下面是一个简单的例子:

#!/usr/bin/env python3

import numpy as np
from mpi4py import MPI
import random

comm = MPI.COMM_WORLD
rank = comm.Get_rank()
root = 0

local_array = [rank] * random.randint(2, 5)
print("rank: {}, local_array: {}".format(rank, local_array))

sendbuf = np.array(local_array)

# Collect local array sizes using the high-level mpi4py gather
sendcounts = np.array(comm.gather(len(sendbuf), root))

if rank == root:
    print("sendcounts: {}, total: {}".format(sendcounts, sum(sendcounts)))
    recvbuf = np.empty(sum(sendcounts), dtype=int)
else:
    recvbuf = None

comm.Gatherv(sendbuf=sendbuf, recvbuf=(recvbuf, sendcounts), root=root)
if rank == root:
    print("Gathered array: {}".format(recvbuf))

如您所见,mpi4py不将sendcounts或recvcounts作为额外参数,而是作为recvbuf参数的tuple/list from。如果传递(recvbuf, sendcounts),它将从recvbuf派生类型。位移/偏移将使来自所有列的数据连续存储并按列排序。在

基本上,mpi4py会猜测各种形式的recvbuf参数的含义。完整而明确的形式是(buffer, counts, displacements, type)。在

关于KeyError的编辑:

很容易混淆的名称rout_arrayset,它不是{}的有效输入。set既不是序列,也没有数组接口。不幸的是,numpy.array没有失败,而是创建了一个非常奇怪的没有维度的ndarray对象。可以在列表中包装阵列创建:

^{pr2}$

集合工作,但是循环没有终止,这并不奇怪,因为在while true循环中没有return或{}。在

相关问题 更多 >