2014-01-23 54 views
2

我试图找出一个方式,采取一个整数numpy的阵列,然后更改的条目,使得最小为0,第二个最小的是1等变化numpy的阵列开始从零

例如

开始与这个

In [13]: a = numpy.array([[1, 2, 10],[1, 2, 99]]) 

In [14]: a 
Out[14]: 
array([[ 1, 2, 10], 
     [ 1, 2, 99]]) 

而得到这样的:

array([[ 0, 1, 2], 
     [ 0, 1, 3]]) 

我可以开始看到的方式,通过与numpy.unique(),例如

In [19]: range(len(b)) 
Out[19]: [0, 1, 2, 3] 

In [20]: b = numpy.unique(a) 

In [21]: b 
Out[21]: array([ 1, 2, 10, 99]) 

In [22]: c = range(len(b)) 

In [23]: c 
Out[23]: [0, 1, 2, 3] 

好像我现在应该可以使用b和c从一个数组转换到另一个。但是,最好(最快)的方法是什么?

+1

可能重复[numpy数组的排名与可能的重复](http://stackoverflow.com/questions/14671013/ranking-of-numpy-array-with-possible-duplicates) – YXD

回答

4

不知道最快的,但如果你有scipy可用,您可以使用scipy.stats.rankdata

>>> a = np.array([[1, 2, 10],[1, 2, 99]]) 
>>> scipy.stats.rankdata(a,'dense').reshape(a.shape)-1 
array([[ 0., 1., 2.], 
     [ 0., 1., 3.]]) 

(需要的reshape,因为它变平首先将数据和-1,因为它开始行列在1)

+0

谢谢,并特别感谢增加的解释。非常整洁的解决方案。 – roblanf

2

最直接的方法是使用argsort()

a = numpy.array([0, 1, 1, 2]) 
u, ind = numpy.unique(a, return_inverse = True) 
u = u.argsort().argsort() 
ret = u[ind] 
+1

如果存在重复索引,则不起作用,例如'[0,1,1,2]'。 – DSM

+0

编辑:现在它也将与重复索引 –

+0

一起使用,注意''np.unique'总是返回排序值,所以'u.argsort()。argsort()== np.arange(len(u))''。 –

2

我给你两个选择,第一,似乎不知何故清洁:

a = numpy.array([[1, 2, 10],[1, 2, 99]]) 
uniq, inv = numpy.unique(a, return_inverse=True) 
result = inv.reshape(a.shape) 

我喜欢这个,因为它与旧版本numpy的的没有return_inverse作品:的

a = numpy.array([[1, 2, 10],[1, 2, 99]]) 
uniq = numpy.unique(a) 
result = uniq.searchsorted(a)