我想在Python中创建一个动态对象(在另一个对象内部),然后向其添加属性。
我试着:
obj = someobject
obj.a = object()
setattr(obj.a, 'somefield', 'somevalue')
但这并不奏效。
什么好主意吗?
编辑:
我设置的属性从一个循环通过一个值的列表,例如。
params = ['attr1', 'attr2', 'attr3']
obj = someobject
obj.a = object()
for p in params:
obj.a.p # where p comes from for loop variable
在上面的例子中,我会得到obj.a。attr1, obj.a。attr2 obj.a.attr3。
我使用了setattr函数,因为我不知道如何从for循环中执行obj.a.NAME。
如何根据上面例子中的p值设置属性?
有关为什么它不起作用的详细信息,请参见不能在“object”类的实例上设置属性。
有不同的类型。Python 3.3+中的SimpleNamespace类:
obj = someobject
obj.a = SimpleNamespace()
for p in params:
setattr(obj.a, p, value)
# obj.a.attr1
collections.namedtuple,打字。NamedTuple可用于不可变对象。PEP 557—数据类建议一个可变的替代方案。
要获得更丰富的功能,可以尝试attrs包。参见示例用法。Pydantic可能也值得一看。
如果你正在寻找链赋值,要做的事情,如django模型模板抽象属性赋值:
from types import SimpleNamespace
def assign(target, *args, suffix):
ls = target
for i in range(len(args) - 1):
a = args[i]
ns = SimpleNamespace()
setattr(ls, a, ns)
ls = ns
setattr(ls, args[-1], suffix)
return ls
a = SimpleNamespace()
assign(a, 'a', 'b', 'c', suffix={'name': 'james'})
print(a.a.b.c)
# {'name': 'james'}
它允许您传递模型作为目标,并分配结束属性给它。