繁体   English   中英

内置函数sum与sum(list,[])有什么关系?

[英]What does the built-in function sum do with sum(list, [])?

当我想展开一个列表时,我找到了如下方式:

>>> a = [[1, 2], [3, 4], [5, 6]]
>>> a
[[1, 2], [3, 4], [5, 6]]
>>> sum(a, [])
[1, 2, 3, 4, 5, 6]

我不知道这些行发生了什么, 文档说明:

sum(iterable[, start])

Sums从左到右startiterable的项目并返回总数。 start默认为0 可迭代的项目是正常的数字,并且start值不允许是一个字符串。

对于某些用例, sum()有很好的替代方法。 连接字符串序列的首选快速方法是调用''.join(sequence) 要以扩展精度添加浮点值,请参阅math.fsum() 要连接一系列迭代,请考虑使用itertools.chain()

版本2.3中的新功能。

难道你不认为开始应该是一个数字? 为什么[]在这里写的?

(sum(a, []))

难道你不认为开始应该是一个数字?

默认情况下, start 一个数字; 0 ,根据您引用的文档。 因此当你这样做时:

sum((1, 2))

它被评估为0 + 1 + 2 ,它等于3 ,每个人都很高兴。 如果你想从不同的号码开始,你可以提供:

>>> sum((1, 2), 3)
6

到现在为止还挺好。


不过,也有其他的东西,你可以用+ ,喜欢列表:

>>> ['foo'] + ['bar']
['foo', 'bar']

但是,如果您尝试使用sum来获得相同的结果,则会得到TypeError

>>> sum((['foo'], ['bar']))

Traceback (most recent call last):
  File "<pyshell#2>", line 1, in <module>
    sum((['foo'], ['bar']))
TypeError: unsupported operand type(s) for +: 'int' and 'list'

因为它现在正在做0 + ['foo'] + ['bar']

要解决这个问题,你可以将自己的start作为[] ,因此它会变成[] + ['foo'] + ['bar'] ,一切都很好。 所以回答:

为什么[]可以写在这里?

因为虽然start默认为一个数字,它并没有成为一个; 其他东西也可以添加,这对于你正在做的事情来说非常方便。

首先,永远不要使用sum来连接/展平列表,因为它具有二次时间,因此与其他方式相比根本没有效率。 它实际上使用了画家算法schlemiel

sum函数在每次迭代时调用start__add__属性,并将迭代的所有项作为第一个参数传递。

例如 :

>>> [].__add__([2,3])
[2, 3]
#OR
>>> [] + [1,2,3]
[1, 2, 3]

在这种情况下,结果将是输入列表的连接列表。 从算法的角度来看,它执行以下操作:

>>> a = [[1, 2], [3, 4], [5, 6]]
>>> start = []
>>> for i in a:
...     start += i
... 
>>> start
[1, 2, 3, 4, 5, 6]

并不是说您可以在具有__add__属性的任何对象序列上调用sum函数,但请注意,如果您的对象不是整数,则默认的start参数为0 ,它将引发TypeError 在这种情况下,您需要为该函数指定正确的start

>>> class newObj(object):
...    def  __init__(self,val):
...         self.val = val
...    def __add__(self,item):
...        return '{}_____{}'.format(self.val,item)
... 
>>> 
>>> start=newObj('new_obj')
>>> 
>>> start
<__main__.newObj object at 0x7f75f9241c50>
>>> 
>>> start + 5
'new_obj_____5'
>>> 
>>> 
>>> sum(['1','2','3'],start)
'new_obj_____123'

您将start与您提供的可迭代内容作为第一个参数相加。 sum不限制int的start type ,以允许各种添加情况。

基本上sum是这样的:

a = [[1, 2], [3, 4], [5, 6]]
sum(a, number)

大致翻译为:

number += every value in the list a

由于列表a中的每个值都是一个列表,因此扩展时的前一个求和看起来像这样:

number + [1, 2] + [3, 4] + [5, 6]

因此,如果输入int这将导致不幸的TypeError因为不允许添加intlist

1 + [1, 2] == I hope you like TypeErrors

但是,如果你输入一个列表[]它只是要的元素加入a一起,导致我们所知道的扁平列表和爱。

start值默认为0int主要是因为最常见的求和情况是算术。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM