2016-08-15 2 views
-1

Предположим, что я определяю следующий класс в Python.Странное поведение экземпляра класса - при обновлении внутренних переменных

class test(): 
    def __init__(self): 
     self.x = 0 
     self.y = self.x ** 2 
    def check(self): 
     self.x = self.x + 1 
     print self.x 
     print self.y 

Здесь у меня есть две внутренние переменные x и y. В инициализации я установил $$ y = x^2 $$. Теперь каждый раз, когда я вызываю метод check(), он увеличивает значение x на 1: self.x = self.x + 1. Однако, когда я печатаю значения х, правильно увеличивается на 1, но всегда остается 0. (Должно быть, это x^2 ??) Что происходит не так?

+0

Ничего не происходит. Вы никогда не меняете 'self.y' после того, как вы инициализировали экземпляр, поэтому он сохраняет то же самое значение, которое у него всегда было. – kindall

+0

Я очень рекомендую Ned Batchelder's [Факты и мифы о именах и знаках Python] (http://nedbatchelder.com/text/names1.html) »(26 минут [видео с PyCon US 2015] (https: // www. youtube.com/watch?v=_AEJHKGk9ns)) для краш-курса в том, как переменные Python и операторы присваивания совсем не похожи на большинство других языков. (В частности, имена всегда ссылаются на значения, _never_ на выражения или другие имена.) –

ответ

2

Ваш self.y присваивается только тогда, когда вы сначала создайте экземпляр своего класса. Он не обновляется каждый раз, когда вы вызываете функцию. Функция def __init__(self): выполняется только тогда, когда вы делаете
myVar = new test(), поэтому значение y присваивается и обновляется только один раз.

Ваш код должен были бы быть:

class test(): 
    def __init__(self): 
     self.x = 0 
     self.y = self.x ** 2 
    def check(self): 
     self.x = self.x + 1 
     self.y = self.x ** 2 
     print self.x 
     print self.y 
2

Python не похож на таблице, где обновление одной ячейки (переменная) может автоматически влиять на ценность другихов.

После инициализации код никогда не меняет значение self.y. Вам нужно добавить код для этого, например.

def check(self): 
     self.x = self.x + 1 
     self.y = self.x ** 2 
     print self.x 
    print self.y 

Существует способ реализовать такое поведение, хотя: использовать properties:

class Test(object): 
    def __init__(self): 
     self._x = 0 
     self.y = 0 

    @property 
    def x(self): 
     return self._x 

    @x.setter 
    def x(self, value): 
     self._x = value 
     self.y = value ** 2 

    def check(self): 
     self.x = self.x + 1 
     print self.x, self.y 

>>> t = Test() 
>>> for i in range(5): 
...  t.check() 
1 1 
2 4 
3 9 
4 16 
5 25 

>>> t.x = 200 
>>> t.y 
40000 

Если вы хотите, вы также можете реализовать y как свойство и он установлен x квадратному корню когда он обновляется. Это обеспечит соблюдение отношения, которое x является квадратным корнем из `y`` и наоборот.

0

Переменная y задана только при ее создании и не обновляется в коде.

У вас должны быть отдельные методы для обновления и/или приращения x и при необходимости отрегулируйте y вместе с вашим методом для проверки значений.

class test(): 
    def __init__(self): 
     self.x = 0 
     self.y = 0 
    def update_x(self, x): 
     self.x = x 
     self.y = x ** 2 
    def increment_x(self): 
     self.x += 1 
     self.y = self.x ** 2 
    def check(self): 
     print self.x 
     print self.y 
Смежные вопросы