这个问题源于PEP 448
-- Additional Unpacking Generalizations并且据我所知存在于 Python 3.5 中(并且没有向后移植到 2.x
)。具体来说,在缺点部分,指出了以下内容:
Whilst
*elements, = iterable
causeselements
to be alist
,elements = *iterable
, causeselements
to be atuple
. The reason for this may confuse people unfamiliar with the construct.
这确实成立,对于 iterable = [1, 2, 3, 4]
,第一种情况产生一个 list
:
>>> *elements, = iterable
>>> elements
[1, 2, 3, 4]
对于第二种情况,创建了一个 tuple
:
>>> elements = *iterable,
>>> elements
(1, 2, 3, 4)
不熟悉这个概念,我很困惑。谁能解释这种行为?带星号的表情是否会根据它所在的一侧而有所不同?
最佳答案
在考虑扩展解包的初始 PEP 时解释了这两种情况之间的区别:PEP 3132 -- Extended iterable unpacking
.
在该 PEP 的摘要中,我们可以看到:
This PEP proposes a change to iterable unpacking syntax, allowing to specify a "catch-all" name which will be assigned a list of all items not assigned to a "regular" name.
(强调我的)
所以第一种情况,执行后:
*elements, = iterable
elements
始终是一个 list
,其中包含 iterable
中的所有项目。
尽管在这两种情况下看起来很相似,但在这种情况下(左侧)的 *
意味着:捕获所有未分配给名称的内容并将其分配给加星标的表达式。它的工作方式与 *args
和 **kwargs
在函数定义中的工作方式类似。
def spam(*args, **kwargs):
""" args and kwargs group positional and keywords respectively """
第二种情况(右侧)有些不同。在这里,我们没有像通常在函数调用中那样以“捕获所有内容”的方式工作的*
。它扩展了它所附加的可迭代对象的内容。所以,声明:
elements = *iterable,
可以看作:
elements = 1, 2, 3, 4,
这是另一种初始化元组
的方法。
请注意,list
可以通过简单地使用 elements = [*iterable]
创建,它将 iterable
的内容解压到 []
并生成 elements = [1, 2, 3, 4]
形式的赋值。
关于python - 赋值语句左侧和右侧的星号 * 运算符,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/35636785/