class Foo(object):
attr_a = 'default_attr_a_value'
attr_b = 'default_attr_b_value'
def __init__(self, *args, **kwargs):
if len(args) >= 2:
self.attr_a = args[0]
self.attr_b = args[1]
if len(args) == 1:
self.attr_a = args[0]
# holds the "emulated" attributes
self._properties = kwargs
def __getattr__(self, name):
if name in self._properties:
return self._properties[name]
else:
raise AttributeError
def __hasattr__(self, name):
return name in self._properties
bar = Foo('modified_value_of_attr_a', **{'aaa':1,'bbb':2})
print bar.attr_a
print bar.attr_b
print bar.aaa
try:
print bar.sss
except AttributeError:
print 'Attribute error raised!'
list_attrs = ['attr_a', 'aaa', 'sss']
for a in list_attrs:
if hasattr(bar, a):
print 'bar, instance of Foo, has an attribute named "%s"' % a
else:
print 'bar, instance of Foo, doesn\'t have an attribute named "%s"' % a
def MyContainer:
def __init__(self, vals={}, **kwvals):
self.__dict__.update(vals, **kwvals)
a = MyContainer({"x":Foo()}, y=Foo()) # there are multiple ways to pass the args
a.x.DoFoo()
from collections import namedtuple
A = namedtuple("A", ["x", "y"])
a = A(Foo(), y=Foo()) # can use positional or keyword arguments
a.x.DoFoo() # this still works!
a.x = "something else" # but this will raise an error
您需要重写
__getattr__
:More to read
自定义类的实例可以用作在其上设置的属性的容器。这可以简单地开始:
要获得作为构造函数的一部分传入所需属性的功能(使用与
dict
构造函数相同的语义),可以使它变得更复杂一些:如果在创建此类容器后不需要添加或删除值,可以改用标准库的
collections.namedtuple
类工厂。您向它传递一个类名和一系列属性名,它将返回一个新类。你知道吗相关问题 更多 >
编程相关推荐