New instance overwrites old values

6

Take a look at this class:

class Signal:
    point = None
    view = {
        "x": None,
        "y": None,
        }
    def __init__(self, point):

        self.point = point

        self.set_position()

        print(self.point + " -> " + str(self.view["x"]) + "x" + str(self.view["y"]))

    def set_position(self):
        if self.point == "north":
            self.view["x"] = 150
            self.view["y"] = 200
        else:
            self.view["x"] = 300
            self.view["y"] = 400

    def check(self):
        print(self.point + " -> " + str(self.view["x"]) + "x" + str(self.view["y"]))

And now in the following result when instantiating 2 different variables like this object and checking the values:

>>> s1 = Signal("north")
north -> 150x200
>>> s2 = Signal("south")
south -> 300x400
>>> s1.check()
north -> 300x400

I just can not find the logic of this. Can you explain me why creating% with% values of s2 are exchanged?

    
asked by anonymous 08.09.2016 / 23:49

2 answers

5

This here ...

class Signal:
    point = None
    view = {
        "x": None,
        "y": None,
        }

    ...

# fim da classe

... does not do what you think it does. Declaring variables at the top of the class in this way causes them to be shared among all copies of the class (similar to% w / o% of other languages). To declare fields in your class, the appropriate way in Python is:

class Signal:

    def __init__(self, point):
        self.point = None
        self.view = {
            "x": None,
            "y": None,
            }

    # demais métodos

# fim da classe

That is, start them in the constructor, putting the same logo at the beginning of the class for ease of reading.

    
09.09.2016 / 00:19
2
  

Can you explain me why creating the s2 values of s1 are exchanged?

Because the variables point and view are attributes of class Signal and not instance.

Class attributes are attributes whose owner is the class itself, which will be shared with all instances of the class. To define unique attributes for an instance, set the variables in __init__ : p>

class Signal:
    def __init__(self, point):
        self.point = point
        self.view = { "x": None,
                      "y": None,
                    }

        self.set_position()

        print(self.point + " -> " + str(self.view["x"]) + "x" + str(self.view["y"]))

See DEMO

More details on documentation .

    
09.09.2016 / 00:19