Python中如何更简洁创建带指定属性的一次性临时对象
针对需要一次性传入带key=42属性临时对象的场景,有两种比namedtuple实现更简便、轻量化的写法:
零依赖最短写法
不需要导入任何模块,直接用内置的type动态创建匿名类实例即可:
f(type('', (), {'key': 42})())
type传入三个参数时会动态创建新类:第一个参数是类名,这里因为类只用一次不会被其他地方引用,传空字符串即可;第二个参数是继承的基类元组,传空元组默认继承object;第三个参数是类的命名空间字典,直接把需要的属性键值对放进去即可。创建完类直接实例化传入函数,用完后类和实例都会被自动回收,没有任何冗余开销。
这种写法不需要导入依赖,不需要提前想临时类名,也没有namedtuple自带的元组索引、拆包、不可变等用不上的多余特性,开销最低,代码长度也更短。
可读性最优写法
如果可以接受一行标准库导入,types.SimpleNamespace是语义最清晰的选择,专门为这种简单属性承载场景设计:
from types import SimpleNamespace f(SimpleNamespace(key=42))
SimpleNamespace不需要提前定义类结构,直接通过关键字参数传入需要的属性即可,原生支持点号属性访问,没有多余的继承方法,比namedtuple的写法更简洁——不需要指定临时类名,也不需要把字段名包裹成列表传入,代码一眼就能看懂是临时属性容器。
不推荐的冗余方案
- 普通自定义类、
dataclass:需要单独写类定义代码、指定类名,对于一次性使用的场景过于繁琐,代码量更大。 - 字典:只能通过
a['key']的下标形式访问值,适配不了函数f里的点号属性访问逻辑,除非修改函数实现,不符合需求。 - 原有
namedtuple方案:除了需要导入依赖外,强制要求指定类型名、传入字段列表,还自带了元组的全套特性,这些功能在当前一次性场景下完全用不上,属于不必要的额外开销。
内容的提问来源于stack exchange,提问作者Paul Jurczak
相关产品推荐
相关产品推荐

