【问题标题】:Python class: How to check whether an attribute is defined inside __init__ or outside __init__Python 类:如何检查属性是在 __init__ 内部还是在 __init__ 外部定义
【发布时间】:2018-02-02 08:29:28
【问题描述】:

如果我有这样的课程:

class A:
    def __init__(self):
        self.a = 1
obj = A()
obj.b = 2

因为我需要编写一个 __setattr__ 方法来修改属性(例如,如果它是在 __init__ 内部定义的,那么做一些事情;如果它是在 外部定义的__init__ 做别的事情。如何确定它是否在 init 中声明?

def __setattr__(self,name,value):
    if name not in self.__dict__:
        self.__dict__['ABC'+ name] = value # add 'ABC' before attribute's name if it was declared in __init__
    else:
        self.__dict__[name] = value # if it was declared outside __init__ then the attribute name doesn't change

【问题讨论】:

  • 你的用例是什么?定义属性的位置没有区别。
  • Python 如此出色的部分原因在于几乎没有特殊情况。 self.a = ... 使用与 obj.b = ... 完全相同的机制......
  • @Daniel Roseman,哦,这就像属性是在 init 中定义的(即名称以 'ABC' 开头,然后当类外的方法尝试更改它们时引发错误
  • 这不是一个用例。它仍然描述了您的解决方案,而不是要解决的根本问题。

标签: python python-3.x


【解决方案1】:

您定义的大多数实例属性或父类(或对象)的行为都将相同,并且在大多数情况下无法区分。如果您出于某种原因真的想区分它们,您应该自己创建一种方法来识别它们,也许可以使用字典来代替。

class A:
    def __init__(self):
        self.my_variables = {'a': 1}

        # Or maintain a list with their names, it seems ugly however
        self.my_variables = ['a']

话虽如此,我一点也不明白你为什么要这样做。也许您应该尝试寻找比覆盖__setattr__ 更简单的问题解决方案。

更新:

在我看来,您试图限制变量的更新,也许是在尝试创建“真正的私有变量”。在我的建议中,不要。从静态语言的角度来看,Python 允许你做很多看起来很疯狂的事情是有原因的。你应该只用_ 开始你的变量,以将它们标记为私有,类似于 Python 推荐的。如果人们无论如何都要访问它们,那么是什么阻止他们找到解决方法来规避您试图强制执行的“限制”?此外,有时访问私有变量是有正当理由的。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2010-11-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2018-11-12
    • 2013-10-17
    • 2012-12-15
    相关资源
    最近更新 更多