如何从Python中删除3D数组中的重复项?

时间:2016-12-10 01:05:12

标签: python numpy

我有一个3D数组如下,' b',我想表示一个二维数组的数组。我想删除我的2-D数组的副本并获得独特的数组。

>>> a = [[[1, 2], [1, 2]], [[1, 2], [4, 5]], [[1, 2], [1, 2]]]
>>> b = numpy.array(a)
>>> b
array([[[1, 2],
        [1, 2]],

       [[1, 2],
        [4, 5]],

       [[1, 2],
        [1, 2]]])

在上面的例子中,我真的想要返回以下内容,因为我想删除一个副本。

unique = array([[[1, 2],
                 [1, 2]],

                 [[1, 2],
                  [4, 5]])

如何使用numpy包呢?感谢

4 个答案:

答案 0 :(得分:0)

参见上一个回答:Remove duplicate rows of a numpy array 转换为元组数组,然后应用np.unique()

答案 1 :(得分:0)

重塑,找到唯一的行,然后再次重塑。

通过转换为集合来查找唯一元组。

import numpy as np
a = [[[1, 2], [1, 2]], [[1, 2], [4, 5]], [[1, 2], [1, 2]]]
b = np.array(a)

new_array = [tuple(row) for row in b.reshape(3,4)]
uniques = list(set(new_array))

output = np.array(uniques).reshape(len(uniques), 2, 2)
output

Out[131]: 
array([[[1, 2],
        [1, 2]],

       [[1, 2],
        [4, 5]]])

答案 2 :(得分:0)

转换为元组并再次返回可能会变得非常昂贵,相反,您可以进行广义视图:

def unique_by_first(a):
    tmp = a.reshape(a.shape[0], -1)
    b = np.ascontiguousarray(tmp).view(np.dtype((np.void, tmp.dtype.itemsize * tmp.shape[1])))
    _, idx = np.unique(b, return_index=True)
    return  a[idx].reshape(-1, *a.shape[1:])

用法:

print unique_by_first(a) 
[[[1 2]
  [1 2]]

 [[1 2]
  [4 5]]]

实际上是对先前answers的概括。

答案 3 :(得分:0)

您可以将每个这样的2D切片从最后两个轴转换为标量,将它们视为多维网格上的索引。目的是基于它们的唯一性将每个这样的切片映射到标量。然后,使用这些标量,我们可以使用np.unique来保留一个实例。

因此,实现将是 -

idx = np.ravel_multi_index(a.reshape(a.shape[0],-1).T,a.max(0).ravel()+1)
out = a[np.sort(np.unique(idx, return_index=1)[1])]

示例运行 -

In [43]: a
Out[43]: 
array([[[8, 1],
        [2, 8]],

       [[3, 8],
        [3, 4]],

       [[2, 4],
        [1, 0]],

       [[3, 0],
        [4, 8]],

       [[2, 4],
        [1, 0]],

       [[8, 1],
        [2, 8]]])

In [44]: idx = np.ravel_multi_index(a.reshape(a.shape[0],-1).T,a.max(0).ravel()+1)

In [45]: a[np.sort(np.unique(idx, return_index=1)[1])]
Out[45]: 
array([[[8, 1],
        [2, 8]],

       [[3, 8],
        [3, 4]],

       [[2, 4],
        [1, 0]],

       [[3, 0],
        [4, 8]]])

如果您不介意维护此类切片的顺序,请跳过最后一步的np.sort()