两个4D numpy数组中所有行的组合

时间:2018-10-16 15:23:40

标签: python arrays numpy

我有两个名为my_arr1, my_arr2的numpy数组,它们的大小均为100x30x30x3。我想输出第一个数组的每一行与第二个数组的每一行的组合,并输出到大小为10000x30x30x3的两个新数组。我设法通过一个简单的示例来做到这一点,该示例具有两个大小为4x2 by following that example的数组:

a1_ = np.array([[1, 1],
           [2, 2],
           [3, 0],
           [4, 2],
           [5, 3]])
a2_ = np.array([[10, 1],
           [11, 2],
           [12, 0],
           [13, 2],
           [14, 3]])


def combine_matrices(a1, a2):

   m1, n1 = a1.shape
   m2, n2 = a2.shape
   out = np.zeros((m1, m2, n1+n2), dtype=int)
   out[:, :, :n1] = a1[:, None, :]
   out[:, :, n1:] = a2
   out.shape = (m1*m2, -1)

 return out

结果是一个25x4数组,可以将其拆分为两个数组25x2。在最终范围为a1 = np.zeros((100, 30, 30, 3))a2 = np.zeros((100. 30, 30, 3))返回两个大小为(10000, 30, 30 ,3)而不仅仅是一个数组的情况下,如何修改函数?

2 个答案:

答案 0 :(得分:1)

您可以使用numpy.outer

完成此操作

虽然不能只使用该函数,但可能会有更好的结果,但是我认为您必须遍历其他矩阵指标。

# Use transpose to make the empty array shape (10x30x30x1000)
out_arr = numpy.zeros(shape=(1000, 30, 30, 10)).transpose()

for i in range(out_arr.shape[0]):
   for j in range(out_arr.dtype[1]):
      for k in range(out_arr.dtype[2]):
          # Use transpose again to get the data you want 
          # (transposing first before grabbing the index) 
          out_arr[i][j][k] = numpy.outer(arr1.transpose()[i][j][k], arr2.transpose()[i][j][k])

# 1000x30x30x10 array (rather than 10x30x30x1000)
out_arr = out_arr.transpose()

我正在使用转置作为技巧,因为您说的数据是(1000,30,30,10)。

让我不胜其烦的一件事是犯了尝试做的错误:

arr[:][i][j][k]

因为在这种情况下,它将无法获取您想要的内存。它获取与以下数据相同的数据:

arr[i][j][k]

答案 1 :(得分:1)

不能100%地确定这是您想要的,但是它能正确显示形状。

首先构建诊断输入

>>> a1 = np.empty((2, 2, 2, 3, 4), 'U1')
>>> for i, x in enumerate(np.ogrid[:2, :2, :2, :3]):
...      a1[..., i] = x
... 
>>> a2 = a1 = a1.view('U4').reshape(a1.shape[:-1])
>>> a1
array([[[['0000', '0001', '0002'],
         ['0010', '0011', '0012']],

        [['0100', '0101', '0102'],
         ['0110', '0111', '0112']]],


       [[['1000', '1001', '1002'],
         ['1010', '1011', '1012']],

        [['1100', '1101', '1102'],
         ['1110', '1111', '1112']]]], dtype='<U4')

接下来,分配输出

>>> A1, A2 = (np.empty((a.shape[0], *a.shape), a.dtype) for a in (a1, a2))

填写广播

>>> A1[...] = a1[:, None]
>>> A2[...] = a2[None]

合并前两个轴

>>> A1, A2 = (A.reshape(-1, *A.shape[2:]) for A in (A1, A2))

完成

>>> A1
array([[[['0000', '0001', '0002'],
         ['0010', '0011', '0012']],

        [['0100', '0101', '0102'],
         ['0110', '0111', '0112']]],


       [[['0000', '0001', '0002'],
         ['0010', '0011', '0012']],

        [['0100', '0101', '0102'],
         ['0110', '0111', '0112']]],


       [[['1000', '1001', '1002'],
         ['1010', '1011', '1012']],

        [['1100', '1101', '1102'],
         ['1110', '1111', '1112']]],


       [[['1000', '1001', '1002'],
         ['1010', '1011', '1012']],

        [['1100', '1101', '1102'],
         ['1110', '1111', '1112']]]], dtype='<U4')
>>> A2
array([[[['0000', '0001', '0002'],
         ['0010', '0011', '0012']],

        [['0100', '0101', '0102'],
         ['0110', '0111', '0112']]],


       [[['1000', '1001', '1002'],
         ['1010', '1011', '1012']],

        [['1100', '1101', '1102'],
         ['1110', '1111', '1112']]],


       [[['0000', '0001', '0002'],
         ['0010', '0011', '0012']],

        [['0100', '0101', '0102'],
         ['0110', '0111', '0112']]],


       [[['1000', '1001', '1002'],
         ['1010', '1011', '1012']],

        [['1100', '1101', '1102'],
         ['1110', '1111', '1112']]]], dtype='<U4')