2016-01-15 2 views
0

У меня есть программа, которая моделирует королевства и другие группы (так называемые «фракции» в моем коде).Где я испортил эту программу для отслеживания альянсов фракций?

class Faction: 
    def __init__(self, name, allies=[]): 
     self.name = name 
     self.allies = allies 

    def is_ally_of(self, other_faction): 
     if self in other_faction.allies: 
      return True 
     else: 
      return False 

    def become_ally(self, other_faction, both_ally=True): 
     """ If both_ally is false, this does *not* also 
      add self to other_faction's ally list """ 
     if self.is_ally_of(other_faction): 
      print("They're already allies!") 
     else: 
      self.allies.append(other_faction) 
      if both_ally == True: 
       other_faction.become_ally(self, False) 

RezlaGovt = Faction("Kingdom of Rezla") 
AzosGovt = Faction("Azos Ascendancy") 

Я хочу быть в состоянии назвать фракции become_ally() для добавления фракций в списки союзников, как это:

RezlaGovt.become_ally(AzosGovt) # Now AzosGovt should be in RezlaGovt.allies, 
           # and RezlaGovt in AzosGovt.allies 

Что на самом деле происходит:

RezlaGovt.become_ally(AzosGovt) 
# prints "They're already allies!" 
# now AzosGovt is in the allies list of both AzosGovt and RezlaGovt, 
# but RezlaGovt isn't in any allies list at all. 

Всякий раз, когда я пытаюсь вызвать стареет(), код должен проверить, чтобы убедиться, что они еще не являются союзниками. Это часть, которая не работает. Каждый раз, когда я вызываю start_ally(), он печатает «Они уже союзники!», Независимо от того, являются ли они на самом деле.

Я также пытался использовать if self in other_faction.allies:, но у этой проблемы была такая же проблема.

Я сильно подозреваю, что проблема связана с моим использованием self, но я не знаю, какие условия для Google для получения дополнительной информации.

+0

В качестве примечания 'если х в у: возвращение Правда еще: возвращение false' может быть упрощена, как' вернуть х в y' – Neitsa

+0

И 'если х == True:' это _usually_ лучше всего выражается как 'if x:' (который принимает что-либо правдоподобное, но Pythonic-код обычно не зависает при использовании 'bool'. – ShadowRanger

ответ

2

You can't use mutable arguments as the default argument to a function.

def __init__(self, name, allies=[]): 

Когда используется по умолчанию, это жеlist каждый раз, так что они имеют один и тот же allies; мутирующий один меняет другой, потому что они на самом деле одно и то же.

Изменить на:

def __init__(self, name, allies=None): 
    if allies is None: 
     allies = [] 

В качестве альтернативы, скопируйте allies аргумент безоговорочно (так что вы не обеспокоены ссылкой на его выживание вне класса и получать мутировали под класс):

def __init__(self, name, allies=[]): 
    self.allies = list(allies) # Which also guarantees a tuple argument becomes list 
           # and non-iterable args are rejected 
1

Измените эту функцию.

def is_ally_of(self, other_faction): 
     if other_faction in self.allies: 
      return True 
     else: 
      return False 

Проверьте свои данные, а не данные переданного объекта.

Также

def __init__(self, name, allies=[]): 

Есть ошибка ждущий, чтобы случиться. Ваш список allies будет статическим списком, общим для всех экземпляров. Вместо того, чтобы использовать

def __init__(self, name, allies=None): 
     self.name = name 
     self.allies = allies or [] 
+1

Первое предложение на самом деле не является проблемой в зависимости от точных целей проектирования (формулировка проблематична, обычно союзники это один из способов, но этот код допускает односторонние альянсы). – ShadowRanger

+0

Да, я разработал его, чтобы разрешить односторонние альянсы, если один народ тайно объявит войну без знания другой нации или какая-то другая странная ситуация, которая может потребовать этого. – Somatic

+0

Функция, вероятно, лучше nam ed 'is_ally'. Существует смешение намерений в вашей функции «стать».У этого есть логика, говоря, что если я не являюсь союзником X, тогда добавьте X в список моих союзников, тогда как это, вероятно, будет больше похоже, если X не является моим союзником, добавьте X в список моих союзников. –

 Смежные вопросы

  • Нет связанных вопросов^_^