2010-02-24 41 views
8

假設我有三個類的系統。 GameClass在初始化時創建其他兩個類的實例。Python OOP - 類關係

class FieldClass: 
    def __init__(self): 
     return 
    def AnswerAQuestion(self):  
     return 42 

class PlayerClass: 
    def __init__(self): 
     return 
    def DoMagicHere(self): 
     # Access "AnswerAQuestion" located in the "FieldClass" instance in "GameClass" 
     pass 

class GameClass: 
    def __init__(self): 
     self.Field = FieldClass() 
     self.Player = PlayerClass() 

什麼是訪問AnswerAQuestion()位於FieldClassPlayerClass實例中的最佳方式是什麼?

  • 是否必須將對FieldClass實例的引用傳遞給PlayerClass
  • 有沒有解決這個問題的另一種更好的方法?這樣做會使我必須在PlayerClass中包含一個額外的變量來保存FieldClass實例。
  • 在Python中是否有完全不同的管理類關係的方法?

回答

6

我會去與Dependency Injection:發起與GameClass所需的構造函數調用等FieldClassPlayerClass(即,而不是創建從GameClass內,你此刻在做相關的對象)。

class GameClass: 
    def __init__(self, fc, pc): 
     self.Field = fc 
     self.Player = pc 

class PlayerClass: 
    def __init__(self, fc): 
     self.fc = fc 

    def DoMagicHere(self): 
     # use self.fc 
     pass 

fc=FieldClass() 
pc=PlayerClass(fc) 
gc=GameClass(fc, pc) 

使用DI,一旦安裝階段完成後,您可以輕鬆訪問所需的成員。

4

爲了更好地瞭解你的班級關係,你必須告訴我們更多關於你的項目和你想要完成的事情。到在你的例子從PlayerClass引用實例的FieldClass

的一種方式是在GameClass實例傳遞給PlayerClass實例:

class PlayerClass: 
    def __init__(self, game): 
     self.game = game 
    def DoMagicHere(self): 
     self.game.Field.AnswerAQuestion() 

# ... 

class GameClass: 
    def __init__(self): 
     self.Field = FieldClass() 
     self.Player = PlayerClass(self) 

另一種方式是通過field可變

class PlayerClass: 
    def __init__(self, field): 
     self.field = field 
    def DoMagicHere(self): 
     self.field.AnswerAQuestion() 
# ... 

class GameClass: 
    def __init__(self): 
     self.Field = FieldClass() 
     self.Player = PlayerClass(self.Field) 

附註:您使用一種特殊的命名方案。我建議這樣:

class Game: 
    def __init__(self): 
     self.field = Field() 
     self.player = Player(...) 

我建議你在讀取壞習慣之前閱讀Python Style Guide

+0

感謝有關命名方案問題 – lamas 2010-02-24 17:47:05

+1

+1的信息,以改進類名的建議。 – 2010-02-24 17:47:41

0

我會做類似以下的事情,在那裏你將Game作爲後向引用傳遞給你,允許你訪問其他相關的類。通過這種方式,您可以選擇爲該玩家實例提供與該字段的直接關係。

class FieldClass(object): 
    def __init__(self, game): 
     self.Game = game 
    def AnswerAQuestion(self):  
     return 42 

class PlayerClass(object): 
    def __init__(self, game): 
     self.Game = game 
     self.Field = game.Field # Optional 
    def DoMagicHere(self): 
     self.Game.Field.AnswerAQuestion() 
     self.Field.AnswerAQuestion() # Optional 

class GameClass(object): 
    def __init__(self): 
     self.Field = FieldClass(self) 
     self.Player = PlayerClass(self) 

一邊注意的是,它是很好的做法,現在有你所有的類都是從object繼承,而不是讓他們獨自站立。

1

你可以提供上下文的子對象,即:

class FieldClass: 
    def __init__(self,game): 
    self.game = game 

class PlayerClass: 
    def __init__(self,game): 
    self.game = game 
    def DoMagicHere(self): 
    self.game.Field.AnswerAQuestion() 

class GameClass: 
    def __init__(self): 
    self.Field = FieldClass(self) 
    self.Player = PlayerClass(self) 

由於對象知道他們的背景下,他們能夠到達在同一背景下,並訪問其他對象。