使用元组列表索引numpy数组

Emr*_*mre 16 numpy multidimensional-array indices

为什么我不能使用像这样的元组索引列表索引ndarray?

idx = [(x1, y1), ... (xn, yn)]
X[idx]
Run Code Online (Sandbox Code Playgroud)

相反,我必须做一些笨拙的事情

idx2 = numpy.array(idx)
X[idx2[:, 0], idx2[:, 1]] # or more generally:
X[tuple(numpy.vsplit(idx2.T, 1)[0])]
Run Code Online (Sandbox Code Playgroud)

有更简单,更pythonic的方式吗?

hpa*_*ulj 28

您可以使用元组列表,但约定与您想要的不同. numpy需要行索引列表,后跟列值列表.显然,您想要指定(x,y)对的列表.

http://docs.scipy.org/doc/numpy/reference/arrays.indexing.html#integer-array-indexing 文档中的相关部分是"整数数组索引".


这是一个例子,在2d数组中寻找3个点.(2d中2分可能令人困惑):

In [223]: idx
Out[223]: [(0, 1, 1), (2, 3, 0)]
In [224]: X[idx]
Out[224]: array([2, 7, 4])
Run Code Online (Sandbox Code Playgroud)

使用你的xy索引对的风格:

In [230]: idx1 = [(0,2),(1,3),(1,0)]
In [231]: [X[i] for i in idx1]
Out[231]: [2, 7, 4]

In [240]: X[tuple(np.array(idx1).T)]
Out[240]: array([2, 7, 4])
Run Code Online (Sandbox Code Playgroud)

X[tuple(zip(*idx1))]是进行转换的另一种方式.该tuple()是Python2可选. zip(*...)是一个Python惯用法,它反转了列表列表的嵌套.

你走在正确的轨道上:

In [242]: idx2=np.array(idx1)
In [243]: X[idx2[:,0], idx2[:,1]]
Out[243]: array([2, 7, 4])
Run Code Online (Sandbox Code Playgroud)

tuple()只是更紧凑(并不一定更'pythonic').鉴于numpy惯例,某种转换是必要的.

(我们应该检查一下n维和m点的作用吗?)