Did something about `namedtuple` change in 3.5.1?

允我心安 提交于 2019-12-03 09:23:05

Per Python bug #24931:

[__dict__] disappeared because it was fundamentally broken in Python 3, so it had to be removed. Providing __dict__ broke subclassing and produced odd behaviors.

Revision that made the change

Specifically, subclasses without __slots__ defined would behave weirdly:

>>> Cluster = namedtuple('Cluster', 'x y')
>>> class Cluster2(Cluster):
    pass
>>> vars(Cluster(1,2))
OrderedDict([('x', 1), ('y', 2)])
>>> vars(Cluster2(1,2))
{}

Use ._asdict().

From the docs

Named tuple instances do not have per-instance dictionaries, so they are lightweight and require no more memory than regular tuples.

The docs (and help(namedtuple)) say to use c._asdict() to convert to a dict.

__dict__ was implemented as a @property and has been removed; you can see the change in the source code:

3.5.0:

def __repr__(self):
    'Return a nicely formatted representation string'
    return self.__class__.__name__ + '({repr_fmt})' % self

@property
def __dict__(self):
    'A new OrderedDict mapping field names to their values'
    return OrderedDict(zip(self._fields, self))

def _asdict(self):
    'Return a new OrderedDict which maps field names to their values.'
    return self.__dict__

def __getnewargs__(self):
    'Return self as a plain tuple.  Used by copy and pickle.'
    return tuple(self)

def __getstate__(self):
    'Exclude the OrderedDict from pickling'
    return None

3.5.1:

def __repr__(self):
    'Return a nicely formatted representation string'
    return self.__class__.__name__ + '({repr_fmt})' % self

def _asdict(self):
    'Return a new OrderedDict which maps field names to their values.'
    return OrderedDict(zip(self._fields, self))

def __getnewargs__(self):
    'Return self as a plain tuple.  Used by copy and pickle.'
    return tuple(self)
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!