如何在类中使用独立于python中创建的任何对象的变量?

如何在类中使用独立于python中创建的任何对象的变量?,python,class,variables,Python,Class,Variables,我想使用一个独立于类可能具有的任何对象的变量: class A: var = 5 ob1 = A() ob2 = A() ob1.var += 2 print ob2.var 我希望一旦ob1将var的值从5修改为7,ob2.var也会显示为7而不是5。我该怎么做?您已经很接近了 class MyData: my_data_var = 4 class A: def fun1(): MyData.my_dat

我想使用一个独立于类可能具有的任何对象的变量:

    class A:
        var = 5
    ob1 = A()
    ob2 = A()
    ob1.var += 2
    print ob2.var
我希望一旦ob1将var的值从5修改为7,ob2.var也会显示为7而不是5。我该怎么做?

您已经很接近了

class MyData:
    my_data_var = 4

class A:
    def fun1():
       MyData.my_data_var += 2

    def fun2():
       return MyData.my_data_var

def main():
    print MyData.my_data_var 
    a = A()
    a.fun1()    
    print a.fun2()
    b = A()
    b.fun1()
    print b.fun2()
    print a.fun1()

main()

这些是静态类变量。。。还有其他类似的方法来利用它们。。。但这是一个简单的快速示例

当您执行
ob1.var+=2
操作时,您不是在修改class属性,而是在创建一个与class属性同名的新实例变量。例如:

>>> ob1 = A()
>>> ob1.var += 2
>>> ob1.__dict__
{'var': 7}
>>> ob1.__class__.__dict__
{'var': 5, '__module__': '__main__', '__doc__': None}
>>> ob1 = A()
>>> ob2 = A()
>>> ob1.var += 2
>>> ob2.var
7
如果要修改class属性,只需使用
A.var+=2
。如果需要从实例执行此操作,可以使用
ob1.\uuuu class\uuuu.var+=2

以下是如何在服务器上使用属性实现所需的行为:

现在使用这个类,当您在
A
的实例上获取或设置
var
变量时,它实际上将获取或设置一个class属性。例如:

>>> ob1 = A()
>>> ob1.var += 2
>>> ob1.__dict__
{'var': 7}
>>> ob1.__class__.__dict__
{'var': 5, '__module__': '__main__', '__doc__': None}
>>> ob1 = A()
>>> ob2 = A()
>>> ob1.var += 2
>>> ob2.var
7

我想您可以使用
属性
执行以下操作:

class Foo(object):
    _var = 5

    @property
    def var(self):
        return self._var

    @var.setter
    def var(self,value):
        self.__class__._var = value

a = Foo()
b = Foo()

a.var += 3
assert a.var == 8
assert b.var == 8

c = Foo()
assert c.var == 8 #(un-instantiated objects pick up the change as well)

class Bar(Foo):
    pass

bar = Bar()
assert bar.var == 8
a.var += 1

#changes to Foo.var affect Bar until a bar object makes it's own changes
assert bar.var == 9    

# changes to a subclass's property don't have any effect on the parent class
bar.var += 2
assert bar.var == 11
assert a.var == 9
如注释中所述,如果您有很多这样的属性,这可能会变得有点乏味。更一般的解决方案是执行以下操作:

class ClassAttribute(object):
    def __init__(self,vname,default=None):
        self.vname = '_'+str(vname)
        self.default = default

    def __get__(self,instance,owner):
        return getattr(owner,self.vname,self.default)

    def __set__(self,instance,value):
        setattr(instance.__class__,self.vname,value)

class Foo(object):
    var = ClassAttribute("var",5)

a = Foo()
b = Foo()
a.var += 2
print a.var
print b.var

根据您希望API的外观,您可以考虑制作<代码> Fun1和<代码> Fun2代码> CaseMease< /Cult> s,并将<代码> MyoDATAAva直接> <代码> A<代码>是的,但我觉得这样做可能不会让一个新的PythOnista感到困惑……但是,我认为您的解决方案是最优雅的一个属性,但是将类属性包装到实例方法中,使其行为类似于实例属性,这是一种浪费。一个完整的自定义描述符意味着setter/getter对于类只存在一次,这对我来说似乎是一种更正确的方法。另一方面,我可以看出,与使用decorators相比,实现它的复杂性被认为是不必要的。@sr2222--添加了一个
ClassAttribute
描述符。有什么想法吗?元类?;)我想真的没有办法让黑客语言看起来既简单、简单、明显又漂亮。@property到底在做什么?当然,对于@var.setter?@IndradhanushGupta--
@property
也有同样的问题,因此当您打印a.var时,
var
函数实际上会被调用。执行
@var.setter
是同一件事,只是它指定了当您试图设置
var
属性
a.var=something