numpy PYTHON:交集索引数组

7z5jn7bk  于 2022-11-10  发布在  Python
关注(0)|答案(5)|浏览(179)

如何获得两个Numy数组之间交点的索引?我可以用intersect1d得到相交值:

import numpy as np

a = np.array(xrange(11))
b = np.array([2, 7, 10])
inter = np.intersect1d(a, b)

# inter == array([ 2,  7, 10])

但是,如何才能将索引设置为inter中的值的a呢?

htrmnn0y

htrmnn0y1#

您可以使用in1d生成的布尔数组来索引arange。颠倒a,使索引与以下值不同:

>>> a[::-1]
array([10,  9,  8,  7,  6,  5,  4,  3,  2,  1,  0])
>>> a = a[::-1]

intersect1d仍然返回相同的值...

>>> numpy.intersect1d(a, b)
array([ 2,  7, 10])

但是in1d返回一个布尔数组:

>>> numpy.in1d(a, b)
array([ True, False, False,  True, False, False, False, False,  True,
       False, False], dtype=bool)

它可用于为范围编制索引:

>>> numpy.arange(a.shape[0])[numpy.in1d(a, b)]
array([0, 3, 8])
>>> indices = numpy.arange(a.shape[0])[numpy.in1d(a, b)]
>>> a[indices]
array([10,  7,  2])

不过,要简化上面的操作,可以使用nonzero--这可能是最正确的方法,因为它返回XY……坐标:

>>> numpy.nonzero(numpy.in1d(a, b))
(array([0, 3, 8]),)

或者,等同地:

>>> numpy.in1d(a, b).nonzero()
(array([0, 3, 8]),)

结果可以用作与a形状相同的数组的索引,没有问题。

>>> a[numpy.nonzero(numpy.in1d(a, b))]
array([10,  7,  2])

但请注意,在许多情况下,只使用布尔数组本身而不是将其转换为一组非布尔索引是有意义的。
最后,您还可以将布尔数组传递给argwhere,它会产生一个形状稍有不同的结果,不太适合索引,但可能用于其他目的。

>>> numpy.argwhere(numpy.in1d(a, b))
array([[0],
       [3],
       [8]])
8e2ybdfx

8e2ybdfx2#

如果需要获取intersect1d给出的唯一值:

import numpy as np

a = np.array([range(11,21), range(11,21)]).reshape(20)
b = np.array([12, 17, 20])
print(np.intersect1d(a,b))

# unique values

inter = np.in1d(a, b)
print(a[inter])

# you can see these values are not unique

indices=np.array(range(len(a)))[inter]

# These are the non-unique indices

_,unique=np.unique(a[inter], return_index=True)

uniqueIndices=indices[unique]

# this grabs the unique indices

print(uniqueIndices)
print(a[uniqueIndices])

# now they are unique as you would get from np.intersect1d()

产出:

[12 17 20]
[12 17 20 12 17 20]
[1 6 9]
[12 17 20]
u0sqgete

u0sqgete3#

indices = np.argwhere(np.in1d(a,b))
zte4gxcn

zte4gxcn4#

对于Python >= 3.5,有另一种解决方案可以这样做

其他解决方案

让我们一步一步地来做这件事。
根据问题中的原始代码

import numpy as np

a = np.array(range(11))
b = np.array([2, 7, 10])
inter = np.intersect1d(a, b)

首先,我们创建一个带零的Numy数组

c = np.zeros(len(a))
print (c)

输出

>>> [ 0.  0.  0.  0.  0.  0.  0.  0.  0.  0.  0.]

其次,使用INTERSECT索引更改c的数组值。因此,我们有

c[inter] = 1
print (c)

输出

>>>[ 0.  0.  1.  0.  0.  0.  0.  1.  0.  0.  1.]

最后一步,利用np.nonzero()的特性,它将精确地返回您想要的非零项的index

inter_with_idx = np.nonzero(c)
print (inter_with_idx)

最终产出

array([ 2, 7, 10])

参考

[1][numpy.nonzero](https://docs.scipy.org/doc/numpy-1.13.0/reference/generated/numpy.nonzero.html)

aemubtdh

aemubtdh5#

从NumPy 1.15.0版开始,intersect1d有一个RETURN_INDEX选项:

numpy.intersect1d(ar1, ar2, assume_unique=False, return_indices=False)

相关问题