为了账号安全,请及时绑定邮箱和手机立即绑定

为什么 __dict__ 不包含类成员,除非使用直接初始化?

为什么 __dict__ 不包含类成员,除非使用直接初始化?

慕沐林林 2023-10-06 16:46:44
我需要访问类方法中的类成员列表,特别是在__init__()函数中,以便集体初始化它们。我尝试使用__dict__andvars(self)但不幸的是它们返回空dict对象,除非使用直接初始化,例如self.y=5. 问题是:为什么它是空的,我如何立即初始化它们,或者本质上变量__dict__适合批量初始化?谢谢示例代码是这样的:class P:    def __init__(self):        print("inside __init__() :",self.y,self.__dict__)    x=8    y=9p=P()print(" y is: ", p.y)print("and __dict__ is:",p.__dict__)输出:inside __init__() : 9 {} y is:  9and __dict__ is: {}Python版本:3.8.5测试的操作系统:windows 10、MacOS 10.15.7 和 Linux CentOS 7
查看完整描述

2 回答

?
幕布斯7119047

TA贡献1794条经验 获得超8个赞

Python 类实例是动态的 - 在您将它们放在那里之前它们没有变量(请参见下面的注释)。他们对这些变量应该是什么没有任何预先了解。通常这是通过将它们一一添加(例如,self.foo = 1)__init__或类中的其他方法来完成的。但如果您有不同的变量源,则可以通过添加到 来实现self.__dict__。假设我有 CSV 文件中的一行,并且我想要一个由该行初始化的类。我可以


class P:

    cell_names = ('a', 'b', 'c')


    def __init__(self, row):

        print("before", self.__dict__)

        self.__dict__.update(zip(self.cell_names, row))

        print("after", self.__dict__)


p = P((1,2,3))

print("attributes", p.a, p.b, p.c)

输出


before {}

after {'a': 1, 'b': 2, 'c': 3}

attributes 1 2 3

当然,还有其他初始化方法。这取决于您的“整体”数据的来源是什么。


如果您想添加所有关键字参数,您可以


class P1:

    def __init__(self, **kw):

        self.__dict__.update(kw)


p = P1(a=1, b=3, c=3)

print("P2", p.a, p.b, p.c)

(注意:您可以使用__slot__在类中预定义变量。这些变量绕过实例字典)


查看完整回答
反对 回复 2023-10-06
?
料青山看我应如是

TA贡献1772条经验 获得超8个赞

_dict__只保存实例属性。在你的例子中是x属性。是一个可以表示许多不同事物的表达方式;实际结果取决于哪个查找首先成功。yself.x

当您进行类似 的分配时self.x = 5,该值将与中的5键相关联。xself.__dict__

当您尝试获取 的值时self.x首先尝试的是self.__dict__['x']。但如果失败了,它会尝试P.x。如果失败,它将检查MRO 中x每个祖先的属性,直到找到值。P如果没有找到任何内容,AttributeError则会引发 an。__getattr__(这忽略了or的使用__getattribute__,但足以解释如何在为空self.x时提供值。)self.__dict__


查看完整回答
反对 回复 2023-10-06
  • 2 回答
  • 0 关注
  • 88 浏览
慕课专栏
更多

添加回答

举报

0/150
提交
取消
意见反馈 帮助中心 APP下载
官方微信