问题描述
如何使用b
将c
中的值累积到a
中以索引a
?也就是说,给定
import numpy as np
a = np.zeros(3)
b = np.array([2, 1, 0, 1])
c = np.arange(0.1, 0.5, 0.1)
print ('a=%s b=%s c=%s'.replace(' ', 'n') % (str(a), str(b), str(c)))
哪些输出
a=[ 0. 0. 0.]
b=[2 1 0 1]
c=[ 0.1 0.2 0.3 0.4]
如何实现
d = np.array([0.3, 0.2 + 0.4, 0.1])
print 'd=%s' % str(d)
哪些输出
d=[ 0.3 0.6 0.1]
使用a
、b
和c
而不使用 for 循环?
我的解决方案尝试
我可以对b
进行排序,然后使用排序的索引对c
进行排序b
p = b.argsort()
print ('b[p]=%s c[p]=%s'.replace(' ', 'n') % (str(b[p]), str(c[p])))
哪些输出
b[p]=[0 1 1 2]
c[p]=[ 0.3 0.2 0.4 0.1]
然后将b
减少到出现次数
occ = np.bincount(b[p])
print 'occ=%s' % str(occ)
哪些输出
occ=[1 2 1]
并使用它来计算部分和
print np.array([np.sum(c[p][0:occ[0]]),
np.sum(c[p][occ[0]:occ[0]+occ[1]]),
np.sum(c[p][occ[0]+occ[1]:occ[0]+occ[1]+occ[2]])])
哪些输出
[ 0.3 0.6 0.1]
我该如何概括这一点?
所有代码和输出
import numpy as np
a = np.zeros(3)
b = np.array([2, 1, 0, 1])
c = np.arange(0.1, 0.5, 0.1)
print ('a=%s b=%s c=%s'.replace(' ', 'n') % (str(a), str(b), str(c)))
d = np.array([0.3, 0.2 + 0.4, 0.1])
print 'd=%s' % str(d)
p = b.argsort()
print ('b[p]=%s c[p]=%s'.replace(' ', 'n') % (str(b[p]), str(c[p])))
occ = np.bincount(b[p])
print 'occ=%s' % str(occ)
print np.array([np.sum(c[p][0:occ[0]]),
np.sum(c[p][occ[0]:occ[0]+occ[1]]),
np.sum(c[p][occ[0]+occ[1]:occ[0]+occ[1]+occ[2]])])
哪些输出
a=[ 0. 0. 0.]
b=[2 1 0 1]
c=[ 0.1 0.2 0.3 0.4]
d=[ 0.3 0.6 0.1]
b[p]=[0 1 1 2]
c[p]=[ 0.3 0.2 0.4 0.1]
occ=[1 2 1]
[ 0.3 0.6 0.1]
np.bincount
完全符合您的要求:
>>> import numpy as np
>>>
>>> b = [2, 1, 0, 1]
>>> c = np.arange(0.1, 0.5, 0.1)
>>> c
array([0.1, 0.2, 0.3, 0.4])
>>> np.bincount(b, c)
array([0.3, 0.6, 0.1])
也有np.add.at
但除非更新非常稀疏a
否则速度要慢得多。
>>> a = np.zeros(3)
>>> np.add.at(a, b, c)
>>> a
array([0.3, 0.6, 0.1])
如果你可以使用熊猫,那么一行解决方案:
import pandas as pd
a = pd.DataFrame({'b':b,'c':c}).groupby('b')['c'].sum().reset_index()
输出:
b c
0 0.3
1 0.6
2 0.1
如果需要 numpy 数组,请将 nessecery 列包装为 numpy:
import pandas as pd
a = pd.DataFrame({'b':b,'c':c}).groupby('b')['c'].sum().reset_index()
b = np.array(a['b'])
c = np.array(a['c'])