我有一个关于继承的基本问题(在python中).我有两个类,其中一个继承自另一个类
class p: def __init__(self,name): self.pname = name class c(p): def __init__(self,name): self.cname = name
有没有可能我可以创建一个父对象和几个引用SAME父对象的子对象?它应该像父对象包含几个变量那样工作,每当我从子进入相应的变量时,我实际上从父进程访问变量.即如果我为一个孩子更改它,它也会被更改为所有其他childes,并且数据只存储在内存中一次(并且不会为每个孩子复制…)
先感谢您.
这是一个可能的解决方法,我不认为这么好
class P: def __init__(self, name): self.pname = name class C: def __init__(self, name,pobject): self.pobject = pobject self.cname = name
这真的是最先进的还是存在其他概念?
塞巴斯蒂安
谢谢大家帮助我,还有名称约定:)但我仍然不是很满意.也许我会举一个更高级的例子来强调我真正想做的事情.
class P: data = "shareddata" def __init__(self,newdata): self.data = newdata def printname(self): print self.name class C(P): def __init__(self,name): self.name = name
现在我可以做到以下几点
In [33]: c1 = test.C("name1") In [34]: c2 = test.C("name2") In [35]: c1.printname() name1 In [36]: c2.printname() name2 In [37]: c1.data Out[37]: 'shareddata' In [38]: c2.data Out[38]: 'shareddata'
到目前为止,这正是我想要的.每个子节点都有一个不同的变量名,父类访问各个变量.正常继承.
然后是来自父类的可变数据,每个子进程都访问它.但是,现在以下内容不再起作用
In [39]: c1.data = "tst" In [40]: c2.data Out[40]: 'shareddata' In [41]: c1.data Out[41]: 'tst'
我希望c1.data中的更改也影响c2.data,因为我希望共享变量,不知何故是这个父类的全局变量.
还有更多.我还想创建P的不同实例,每个实例都有自己的数据变量.当我创建一个新的C对象时,我想指定哪个P对象数据应该是athetited,即共享….
更新:
评论@eyquem的评论:谢谢你,它正朝着我想要的方向前进.但是,现在__class __.pvar在类的所有对象之间共享.我想要的是P的几个实例可能有不同的pvar.让我们假设P1有pvar = 1而P2有pvar = 2.然后我想创建与P1相关的子C1a,C1b,C1c,即如果我说C1a.pvar它应该从P1获得pvar.然后我创建C2a,C2b,C2c,如果我访问,即C2b.pvar,我想从P2访问pvar.由于C类从P类继承pvar,因此C的已知.我天真的想法是,如果我创建CI的新实例应该能够指定哪个(现有的)P对象应该用作父对象而不是创建一个全新的P对象,就像在C的__init__中调用P .__ init__一样…这听起来很简单,也许我忘记了……
更新:
所以我找到了this discussion这几乎是我的问题
有什么建议?
更新:
方法.class._subclasses_似乎不再存在..
更新:
这是另一个链接:
link to discussion
它通过复制解决.但我不想复制父类,因为我希望它只存在一次……
更新:
很抱歉昨天离开讨论,我有点不舒服…谢谢你的帖子!我现在将通读它们.我考虑了一下,这是我找到的可能的解决方案
class P(object): def __init__(self,pvar): self.pobject = None self._pvar = pvar @property def pvar(self): if self.pobject != None: return self.pobject.pvar else: return self._pvar @pvar.setter def pvar(self,val): if self.pobject != None: self.pobject.pvar = val else: self._pvar=val def printname(self): print self.name class C(P): def __init__(self,name,pobject): #<-- The same default `P()` is # used for all instances of `C`, # unless pobject is explicitly defined. P.__init__(self,None) self.name = name self.pobject = pobject p1 = P("1") p2 = P("2") c1a = C("c1a",p1) c1b = C("c1b",p1) c1c = C("c1c",p1) c2a = C("c2a",p2) c2b = C("c2b",p2) c2c = C("c2c",p2) print id(c1a.pvar) print id(c1b.pvar) print id(c1c.pvar) print id(c2a.pvar) print id(c2b.pvar) print id(c2c.pvar) print id(p1.pvar) print id(p2.pvar) print id(c1a.name) print id(c1b.name) print id(c1c.name) print id(c2a.name) print id(c2b.name) print id(c2c.name)
这有点麻烦,我希望有一种更简单的方法来实现这一点.但它的特点是pvar只在P类中提到,C类不知道pvar,因为它应该根据我对继承的理解.然而,当我创建一个新的C实例时,我可以指定一个现有的P实例,它将存储在变量pobject中.当访问变量pvar时,实际访问存储在该变量中的P实例的pvar …
输出由.给出
3078326816 3078326816 3078326816 3074996544 3074996544 3074996544 3078326816 3074996544 156582944 156583040 156583200 156583232 156583296 156583360
我现在将通过你的上一篇评论阅读,
一切顺利,塞巴斯蒂安
更新:
我认为最优雅的方式是以下(不起作用)
class P(object): def __init__(self,pvar): self.pvar = pvar def printname(self): print self.name class C(P): def __init__(self,name,pobject): P = pobject self.name = name
我认为python应该允许这个……
更新:
好的,由于eyquem的解释,现在我找到了实现这一目标的方法.但由于这真的是一个黑客应该有一个相同的官方版本…
def replaceinstance(parent,child): for item in parent.__dict__.items(): child.__dict__.__setitem__(item[0],item[1]) print item class P(object): def __init__(self,pvar): self.pvar = pvar def printname(self): print self.name class C(P): def __init__(self,name,pobject): P.__init__(self,None) replaceinstance(pobject,self) self.name = name p1 = P("1") p2 = P("2") c1a = C("c1a",p1) c1b = C("c1b",p1) c1c = C("c1c",p1) c2a = C("c2a",p2) c2b = C("c2b",p2) c2c = C("c2c",p2) print id(c1a.pvar) print id(c1b.pvar) print id(c1c.pvar) print id(c2a.pvar) print id(c2b.pvar) print id(c2c.pvar) print id(p1.pvar) print id(p2.pvar) print id(c1a.name) print id(c1b.name) print id(c1c.name) print id(c2a.name) print id(c2b.name) print id(c2c.name)
输出与上面相同
3077745184 3077745184 3077745184 3074414912 3074414912 3074414912 3077745184 3074414912 144028416 144028448 144028480 144028512 144028544 144028576
更新:即使id似乎是正确的,最后的代码也不能正常工作,因为这个测试很明显
c1a.pvar = "newpvar1" print c1a.pvar print c1b.pvar print c1c.pvar print c2a.pvar print c2b.pvar print c2c.pvar print p1.pvar print p2.pvar
它有输出
newpvar1 1 1 2 2 2 1 2
然而,我发布的版本首先工作:
class P(object): def __init__(self,pvar): self.pobject = None self._pvar = pvar @property def pvar(self): if self.pobject != None: return self.pobject.pvar else: return self._pvar @pvar.setter def pvar(self,val): if self.pobject != None: self.pobject.pvar = val else: self._pvar=val def printname(self): print self.name class C(P): def __init__(self,name,pobject): #<-- The same default `P()` is # used for all instances of `C`, # unless pobject is explicitly defined. P.__init__(self,None) self.name = name self.pobject = pobject p1 = P("1") p2 = P("2") c1a = C("c1a",p1) c1b = C("c1b",p1) c1c = C("c1c",p1) c2a = C("c2a",p2) c2b = C("c2b",p2) c2c = C("c2c",p2) print id(c1a.pvar) print id(c1b.pvar) print id(c1c.pvar) print id(c2a.pvar) print id(c2b.pvar) print id(c2c.pvar) print id(p1.pvar) print id(p2.pvar) print id(c1a.name) print id(c1b.name) print id(c1c.name) print id(c2a.name) print id(c2b.name) print id(c2c.name) print "testing\n" c1a.printname() c1b.printname() c1c.printname() c2a.printname() c2b.printname() c2c.printname() print "\n" c1a.name = "c1anewname" c2b.name = "c2bnewname" c1a.printname() c1b.printname() c1c.printname() c2a.printname() c2b.printname() c2c.printname() print "pvar\n" print c1a.pvar print c1b.pvar print c1c.pvar print c2a.pvar print c2b.pvar print c2c.pvar print p1.pvar print p2.pvar print "\n" c1a.pvar = "newpvar1" print c1a.pvar print c1b.pvar print c1c.pvar print c2a.pvar print c2b.pvar print c2c.pvar print p1.pvar print p2.pvar print "\n" c2c.pvar = "newpvar2" print c1a.pvar print c1b.pvar print c1c.pvar print c2a.pvar print c2b.pvar print c2c.pvar print p1.pvar print p2.pvar
与输出
3077745184 3077745184 3077745184 3074414912 3074414912 3074414912 3077745184 3074414912 144028416 144028448 144028480 144028512 144028544 144028576 testing c1a c1b c1c c2a c2b c2c c1anewname c1b c1c c2a c2bnewname c2c pvar 1 1 1 2 2 2 1 2 newpvar1 newpvar1 newpvar1 2 2 2 newpvar1 2 newpvar1 newpvar1 newpvar1 newpvar2 newpvar2 newpvar2 newpvar1 newpvar2
有人知道为什么会这样吗?我可能不明白python与__dict__一起使用的内部方式……
It should work like that that the parent object contains several variables and whenever I access the corresponding variables from a child I actually access the variable form the parent. I.e. if I change it for one child it is changed also for all other childes and the data are only stored once in memory (and not copied for each child…)
那不是继承.
这是一个完全不同的概念.
您的“共享变量”只是可以变异的对象,并且在其他对象中具有引用.没什么有趣的.
继承与此完全不同.