9

按照这个技巧来获取 NumPy 数组的唯一条目,我现在有一个双列数组,基本上是成对的,第一个元素在 [0.9:0.02:1.1] 范围内,第二个元素在 [1.5:0.1:2.0 范围内]。让我们称之为A. 目前,它完全未排序,即

In [111]: A
Out[111]: 
array([[ 1.1 ,  1.9 ],
       [ 1.06,  1.9 ],
       [ 1.08,  1.9 ],
       [ 1.08,  1.6 ],
       [ 0.9 ,  1.8 ],
       ...
       [ 1.04,  1.6 ],
       [ 0.96,  2.  ],
       [ 0.94,  2.  ],
       [ 0.98,  1.9 ]])

我想对其进行排序,以便每一行首先在第二列中增加,然后在第一列中增加。IE

array([[ 0.9 ,  1.5 ],
       [ 0.9 ,  1.6 ],
       [ 0.9 ,  1.7 ],
       [ 0.9 ,  1.9 ],
       [ 0.9 ,  1.9 ],
       [ 0.9 ,  2.  ],
       [ 0.92,  1.5 ],
       ...
       [ 1.08,  2.  ],
       [ 1.1 ,  1.5 ],
       [ 1.1 ,  1.6 ],
       [ 1.1 ,  1.7 ],
       [ 1.1 ,  1.8 ],
       [ 1.1 ,  1.9 ],
       [ 1.1 ,  2.  ]])

但我找不到同时提供两者的排序算法。正如这里所建议的,我已经尝试过A[A[:,0].argsort()]and A[A[:,1].argsort()],但它们每列只排序一列。我也尝试过同时应用两者,但发生了同样的事情。

如果我错过了一些简单的东西,我深表歉意,但我已经找了一段时间了......

4

3 回答 3

7

numpy.lexsort将在这里工作:

A[np.lexsort(A.T)]

您需要A在将其传递给 lexsort 之前进行转置,因为当传递一个二维数组时,它期望按行排序(最后一行、倒数第二行等)。

另一种可能更清晰的方法是显式传递列:

A[np.lexsort((A[:, 0], A[:, 1]))]

您仍然需要记住 lexsort 首先按最后一个键排序(这可能有一些很好的理由;这与对连续键执行稳定排序相同)。

于 2012-09-19T14:13:12.180 回答
4

以下将起作用,但可能有更快的方法:

A = np.array(sorted(A,key=tuple))
于 2012-09-19T14:13:37.250 回答
3

只需将整个事物(包括独特的部分)替换为A2D:

A = np.ascontiguousarray(A) # just to make sure...
A = A.view([('', A.dtype)] * A.shape[1])

A = np.unique(A)
# And if you want the old view:
A = A.view(A.dtype[0]).reshape(-1,len(A.dtype))

我希望您不要使用set链接问题中的解决方案,除非您不太关心速度。lexsort等通常很好,但这里没有必要,因为默认排序会做(如果它是一个recarray )


编辑:不同的视图(结果几乎相同),但可能更优雅一点,因为不需要重塑:

A = A.view([('', A.dtype, A.shape[0])])
A = np.unique(A)
# And to go back
A = A.view(A.dtype[0].base)
于 2012-09-19T14:28:31.950 回答