优化函数切片numpy数组



i具有以下功能,该功能以浮点数为单位和一个整数作为参数。数组"计数"中的每一行都是一些实验的结果,我想随机绘制实验列表并添加它们,然后重复此过程以创建许多样本组。

def my_function(counts,nSamples):
    ''' Create multiple randomly drawn (with replacement)
        samples from the raw data '''
    nSat,nRegions = counts.shape
    sampleData = np.zeros((nSamples,nRegions))
    for i in range(nSamples):
        rc = np.random.randint(0,nSat,size=nSat)
        sampleData[i] = counts[rc].sum(axis=0)
    return sampleData

此功能看起来很慢,通常计数约为100,000行(和4列(,而nsamples大约在2000年。我尝试使用numba和隐式循环来尝试加速此代码而没有成功。尝试提高速度的其他方法还有哪些?

我在功能上运行了CPROFILE,并获得了以下输出。

8005函数在60.208秒内调用

订购:标准名称

   ncalls  tottime  percall  cumtime  percall filename:lineno(function)
    1    0.000    0.000   60.208   60.208 <string>:1(<module>)
 2000    0.010    0.000   13.306    0.007 _methods.py:31(_sum)
    1   40.950   40.950   60.208   60.208 optimize_bootstrap.py:25(bootstrap)
    1    0.000    0.000    0.000    0.000 {method 'disable' of '_lsprof.Profiler' objects}
 2000    5.938    0.003    5.938    0.003 {method 'randint' of 'mtrand.RandomState' objects}
 2000   13.296    0.007   13.296    0.007 {method 'reduce' of 'numpy.ufunc' objects}
 2000    0.015    0.000   13.321    0.007 {method 'sum' of 'numpy.ndarray' objects}
    1    0.000    0.000    0.000    0.000 {numpy.core.multiarray.zeros}
    1    0.000    0.000    0.000    0.000 {range}

您确定

是否确定

rc = np.random.randint(0,nSat,size=nSat)

是您想要的,而不是size=someconstant?否则,您将在所有行中总结很多重复。


编辑用矩阵产品完全替换切片吗?

rcvec=np.zeros(nSat,np.int) for i in rc: rcvec[i]+=1 sampleData[i] = rcvec.dot(counts)

(也许Numpy中有一个函数可以更快地为您提供RCVEC(

简单地生成一个与np.random.randint2D大小一起生成所有索引,使用这些索引将其索引到counts阵列中,然后沿着第一个轴汇总,就像您使用Loopopy One一样。

因此,一种矢量化的方式,速度更快,就像这样 -

RC = np.random.randint(0,nSat,size=(nSat, nSamples))
sampleData_out = counts[RC].sum(axis=0)

最新更新