创建作为该类实例的类成员的最“ pythonic”方法是什么?即像这样的东西:
class MyClass:
# error! (and this is to be expected as MyClass is not yet fully defined)
instance_as_member = MyClass()
def __init__(self):
print("MyClass instance created!")
可以通过在类定义之后添加成员来解决此问题:
class MyClass:
...
MyClass.instance_as_member = MyClass()
但这似乎有点错误;自然,应该在该类的 中定义该类的成员。
有更好的方法吗?
答案 0 :(得分:2)
这不是“有点不对劲”-这是简单明了的方法。 一行代码,每个人都可以读取,并且显而易见是“它是什么”。
它仍然没有“感觉”优雅。 因此,如果您不想只是为了外观而这样做,并且也许,如果有很多这样的类而不重复代码,则可以使用类装饰器来完成:
def instance_as_member(attr_name='instance_as_member', *init_args, **init_kwargs):
def decorator(cls):
instance = cls(*init_args, **init_kwargs)
setattr(cls, attr_name, instance)
return cls
return decorator
@instance_as_member()
class MyClass:
...
装饰者可以做到这一点,因为它们会在完全创建完后将cls修改为参数。对于元类,这将很棘手,因为类实例化的某些步骤(如调用__init_subclass__
会在所有可以被覆盖的显式元类方法之后之后执行,因此,尝试创建一个元类方法可能会遇到问题。元类初始化方法({{1},__init__
或元元类的__new__
)中的实例
答案 1 :(得分:0)
您似乎需要setUp
类型的功能。这是在类内执行此操作的一种“稍脏”方法:设置类变量标志以表示该类的首次使用。检查实例化标志;如果这是第一次访问,请清除该标志并运行设置方法。
class MyClass:
first_touch = True
def __init__(self, id=0):
if MyClass.first_touch:
MyClass.setUp(id)
print("MyClass instance created!", id)
@classmethod
def setUp(self, id):
MyClass.first_touch = False
MyClass.instance_as_member = MyClass(-999)
print("Start")
local_obj = MyClass(1)
local_obj = MyClass(2)
local_obj = MyClass(3)
答案 2 :(得分:0)
虽然该类未在主体内定义,但在__init__
但是,存在一个问题,即在__init__
中实例化该类是递归的,因此您需要跟踪instance_as_member
是否已经完成。
类似于以下作品:
class Foo:
member_added = False
instance_as_member = None
def __init__(self):
if not Foo.member_added:
Foo.member_added = True
Foo.instance_as_member = Foo()
print(Foo.instance_as_member)
Foo()
print(Foo.instance_as_member)
结果是:
没有
<__ main__.Foo对象位于0x7fcd9f68f3c8>
(关于这是否一个好主意是完全不同的问题!)