2011-06-07 85 views
0

這是我爲我發現的問題創建的測試用例。Python對象持有對象的字典()

由於某些原因,B()中的dict()'l'似乎不具有正確的值。在我的Linux 11.04 Ubuntu,python 2.7.1+上查看下面的輸出。

class A(): 
    name = None 
    b = None 
    def __init__(self, name, bname, cname, dname): 
     self.name = name 
     print "A: name", name 
     self.b = B(name, bname, cname, dname) 
     print "A self.b:", self.b 

class B(): 
    name = None 
    l = dict() 
    c = None 
    def __init__(self, name, bname, cname, dname): 
     self.aname = name 
     self.name = bname 
     print " B: name", bname 
     self.c = C(bname, cname, dname) 
     self.l["bb"] = self.c 
     print " B self:", self 
     print " B self.c:", self.c 
     print " B self.l[bb]:", self.l["bb"], "<<<OK>>>" 

    def dump(self): 
     print " A: name", self.aname 
     print " B: name", self.name 
     for i in self.l: 
      print " B: i=", i, "self.l[i]", self.l[i], "<<<ERROR>>>" 

class C(): 
    name = None 
    l = dict() 
    d = None 
    def __init__(self, bname, cname, dname): 
     self.bname = bname 
     self.cname = cname 
     print " B: name", bname 
     print " C: name", cname 
     print " C self:", self 

    def dump(self): 
     print " B name:", self.bname 
     print " C name:", self.cname 

a1 = A("a1", "b1", "c1", "d1") 
a2 = A("a2", "b2", "c2", "d2") 
a3 = A("a3", "b3", "c3", "d3") 

a1.b.dump() 
a1.b.c.dump() 
a2.b.dump() 
a2.b.c.dump() 
a3.b.dump() 
a3.b.c.dump() 

輸出我的機器上:

$ python bedntest.py 
A: name a1 
B: name b1 
    B: name b1 
    C: name c1 
    C self: <__main__.C instance at 0xb76f3a6c> 
B self: <__main__.B instance at 0xb76f388c> 
B self.c: <__main__.C instance at 0xb76f3a6c> 
B self.l[bb]: <__main__.C instance at 0xb76f3a6c> <<<OK>>> 
A self.b: <__main__.B instance at 0xb76f388c> 
A: name a2 
B: name b2 
    B: name b2 
    C: name c2 
    C self: <__main__.C instance at 0xb76f3acc> 
B self: <__main__.B instance at 0xb76f3aac> 
B self.c: <__main__.C instance at 0xb76f3acc> 
B self.l[bb]: <__main__.C instance at 0xb76f3acc> <<<OK>>> 
A self.b: <__main__.B instance at 0xb76f3aac> 
A: name a3 
B: name b3 
    B: name b3 
    C: name c3 
    C self: <__main__.C instance at 0xb76f3b2c> 
B self: <__main__.B instance at 0xb76f3b0c> 
B self.c: <__main__.C instance at 0xb76f3b2c> 
B self.l[bb]: <__main__.C instance at 0xb76f3b2c> <<<OK>>> 
A self.b: <__main__.B instance at 0xb76f3b0c> 
A: name a1 
B: name b1 
B: i= bb self.l[i] <__main__.C instance at 0xb76f3b2c> <<<ERROR>>> 
    B name: b1 
    C name: c1 
A: name a2 
B: name b2 
B: i= bb self.l[i] <__main__.C instance at 0xb76f3b2c> <<<ERROR>>> 
    B name: b2 
    C name: c2 
A: name a3 
B: name b3 
B: i= bb self.l[i] <__main__.C instance at 0xb76f3b2c> <<<ERROR>>> 
    B name: b3 
    C name: c3 

據我瞭解,以上各行:

B: i= bb self.l[i] <__main__.C instance at 0xb76f3b2c> <<<ERROR>>> 

都應該持有C(唯一的實例),如在初始化時看到 - 不是最後創建的實例(請參閱< < <確定>>>行)。

這裏發生了什麼事?

+0

可以減少在較少的線路錯誤? – 2011-06-07 06:55:45

回答

1

看起來你正試圖在類級別「聲明」實例屬性。類屬性在Python的自己的具體用途,這是錯誤的把它們放在那裏,如果你不打算使用過的類屬性

class A(): 
    name = None # Don't do this 
    b = None  # Don't do this 
    def __init__(self, name, bname, cname, dname): 
     self.name = name 
     print "A: name", name 
     self.b = B(name, bname, cname, dname) 
     print "A self.b:", self.b 

class B你創建了一個類屬性l。由於該實例沒有它自己的屬性l它使用該類的屬性。

你可以只寫你的B類這樣反而

class B(): 
    def __init__(self, name, bname, cname, dname): 
     self.aname = name 
     self.name = bname 
     self.l = dict() 
     print " B: name", bname 
     self.c = C(bname, cname, dname) 
     self.l["bb"] = self.c 
     print " B self:", self 
     print " B self.c:", self.c 
     print " B self.l[bb]:", self.l["bb"], "<<<OK>>>" 

... 
+0

真的把事情放在不同的角度 - 謝謝! – 2011-06-07 07:37:15

+0

@Hinko,你很受歡迎 – 2011-06-07 11:28:48

6

發生了什麼事是您創建了一個類屬性。通過在__init__()中實例化來創建實例屬性。

+3

+1爲了簡潔,清晰,並且還抵制了面對代碼牆時運行的初始衝動:) – slezica 2011-06-07 06:45:10

+0

感謝您幫助完成noob :),因爲我需要看第二個答案才能最終理解:( – 2011-06-07 07:36:36