新更新:
在 python 3.6+ 中,您可以使用新的类型化语法并创建一个typing.NamedTuple。新语法支持所有常见的 python 类创建功能(文档字符串、多重继承、默认参数、方法等从 3.6.1 开始可用):
import typing
class Pokemon(MyMixin, typing.NamedTuple):
"""
Attributes
----------
name : str
What do you call your Pokemon?
type : str
grass, rock, electric, etc.
level : int
Experience level [0, 100]
"""
name: str
type: str
level: int = 0 # 3.6.1 required for default args
def method(self):
# method work
这个版本创建的类对象大多等同于原来的collections.namedtuple、except for a few details。
您也可以使用与旧命名元组相同的语法:
Pokemon = typing.NamedTuple('Pokemon', [('name', str), ('type', str), ('level', int)])
原答案
简答:no, unless you are using Python < 3.5
P3 docs 似乎非常清楚地暗示,除非您需要添加计算字段(即描述符),否则子类化 namedtuple 不被视为规范方法。这是因为您可以直接更新文档字符串(从 3.5 开始,它们现在是可写的!)。
子类化对于添加新的存储字段没有用处。相反,只需从 _fields 属性创建一个新的命名元组类型...
可以通过直接分配给__doc__ 字段来自定义文档字符串...
更新:
在最新版本的 Python 中,轻量级数据类现在还有其他几个引人注目的可能性。
一个是types.SimpleNamespace (Python 3.3 and later)。它的结构不像namedtuple,但结构并不总是必要的。
关于SimpleNamespace 需要注意的一点:默认情况下,需要在实例化类时显式指定字段名称。不过,这可以很容易地解决,只需致电super().__init__:
from types import SimpleNamespace
class Pokemon(SimpleNamespace):
"""
Attributes
----------
name : str
What do you call your Pokemon?
type : str
grass, rock, electric, etc.
level : int
Experience level [0, 100]
"""
__slots__ = ("name", "type", "level")
# note that use of __init__ is optional
def __init__(self, name, type, level):
super().__init__(name=name, type=type, level=level)
另一个有趣的选项——which is available as of Python 3.7——是dataclasses.dataclass(另见PEP 557):
from dataclasses import dataclass
@dataclass
class Pokemon:
__slots__ = ("name", "type", "level")
name: str # What do you call your Pokemon?
type: str # grass, rock, electric, etc.
level: int = 0 # Experience level [0, 100]
请注意,默认情况下,这两个建议都是可变的,__slots__ 不是任何一个都需要。