鉴于S = 25的数量且列表L = [10,20,30],我希望以下列方式将S分配给L: 输出 - > [10,15,0]
我编写了以下代码,完成了这项工作:
S = 25
l = [10,20,30]
res= []
b = True
for value in l:
if b == True:
if S - value >0:
res.append(value)
else:
res.append(S)
b= False
S -= value
else:
res.append(0)
是否有可能重写它,可能是一个单行? (允许numpy)
答案 0 :(得分:2)
稍短且更易读:
def distribute(S, L):
res = []
for e in L:
res.append(min(e, S))
S = max(0, S-e)
return res
虽然你可以使这个(或任何真正的)单行,但我不会强迫它。保持可读性更好。
您还可以使用等效的生成器函数:
def distribute(S, L):
for e in L:
yield min(e, S)
S = max(0, S-e)
list(distribute(S, l))
答案 1 :(得分:1)
这是一种方式,但请不要因为他们是单行而加入单行。在可读性或性能方面,它们通常不是最好的方法。
from itertools import accumulate
S = 25
l = [10, 20, 30]
res = [i if j <= S else max(0, S-k) \
for i, j, k in zip(l, accumulate(l), accumulate([0]+l))]
# [10, 15, 0]
答案 2 :(得分:0)
由于OP特别要求numpy
,所以我们假设这是关于大型数组的。我认为OP主题中的distribute
是一个关键字,因为这与PDF和CDF(https://en.wikipedia.org/wiki/Cumulative_distribution_function)之间的转换以及反之非常相似:
a = numpy.array([10, 20, 30])
c = a.cumsum() # [10, 30, 60]
b = c.clip(0, 25) # [20, 25, 25]
numpy.ediff1d(b, to_begin=b[0]) # [10, 15, 0]