2017-12-13 3 views
1

Numpy 최적화 버전 인 역함수 numpy.bincounts을 만들려고합니다. bincounts은 일대일 버전이 아니므로 가장 간단한 버전에 대해 이야기 해 보겠습니다.numpy.bincounts의 반대?

import numpy as np 


def bincounts_inverse(counts): 
    list = [] 
    dtype = np.min_scalar_type(counts.shape[0] - 1) 
    for bin, count in enumerate(counts): 
     ar = np.empty(count, dtype=dtype) 
     ar[:] = bin 
     list.append(ar) 

    return np.concatenate(list) 

이것은 아마도 Numpy와 Python에 대한 현재 지식을 얻을 수있는 최상의 방법입니다. 카운트가 높고 빈도가 낮지 만 속도가 느릴 때 속도가 매우 빨라집니다. 반대의 경우에는 속도가 느려집니다. 그것은 점근 적으로 최적이지만 아마 당신이 할 수있는 최선은 아닙니다.

더 빠른 방법이 있나요?

다음은 샘플 입출력입니다.

counts = np.array([3, 1, 0, 2, 5], np.uint8) 
bincounts_inverse(counts) = np.array([0, 0, 0, 1, 3, 3, 4, 4, 4, 4, 4], 
            dtype=np.uint8) 
+1

샘플 입력과 예상 출력을 제공 할 수 있습니까? 도움이 될 것입니다. –

+0

@ cᴏʟᴅs my 나는 그것을 내 대답에 추가 할 것이다, 고마워. –

답변

3

bincount의 역이 될 것이다 repeat -

np.repeat(np.arange(len(counts)), counts) 

샘플 실행 - 비 - 제로 인덱스를 사용하고이 sparseycounts더 효율적으로 될 수와

In [22]: counts = np.array([3,0,2,1,0,2]) 

In [23]: list = [] 
    ...: dtype = np.min_scalar_type(counts.shape[0] - 1) 
    ...: for bin, count in enumerate(counts): 
    ...:  ar = np.empty(count, dtype=dtype) 
    ...:  ar[:] = bin 
    ...:  list.append(ar) 
    ...: out = np.concatenate(list) 

In [24]: out 
Out[24]: array([0, 0, 0, 2, 2, 3, 5, 5], dtype=uint8) 

In [25]: np.repeat(np.arange(len(counts)), counts) 
Out[25]: array([0, 0, 0, 2, 2, 3, 5, 5]) 

또 다른 -

idx = np.flatnonzero(counts!=0) 
out = np.repeat(idx, counts[idx])