jinhwan
jinhwan

Reputation: 1227

python member variable of instance works like member variable, and some works like static variable

i'm python newbie, and member variable of class works weird in my python code. some works like normal variable, but some works like static variable!

class Chaos:
    list_value = []
    value = "default"

    def set_value(self, word):
        self.list_value.append(word)
        self.value = word 

    def show(self, num):
        print(str(num) + "====")
        print("value : " + self.value)
        for st in self.list_value:
            sys.stdout.write(st)
        print("\n=====\n")

a = Chaos()
a.show(0)
a.set_value("A")
a.show(1)
b = Chaos()
a.show(2)
b.show(3)

result

0====
value : default

=====

1====
value : A
A
=====

2====
value : A
A
=====

3====
value : default
A
=====

but the last result of the test is different from what i expected in last test. There should be no "A" in the 'list_value' of the instance of 'b'. It was just created, and never have been added 'A' before. I added 'A' to the instance of 'a', not 'b'. But the result show me that there are also 'A' in 'b' More over, the 'list_value' and the 'value' in the class works differently. It looks like the both have same syntax. why do they work differently?

Upvotes: 12

Views: 19592

Answers (2)

mgibsonbr
mgibsonbr

Reputation: 22007

Those are, in fact, class variables. To create instance variables, initialize them in the __init__ function:

class Chaos:
    def __init__(self):
        self.list_value = []
        self.value = "default"

The reason value is behaving like instance variables is because you're setting it using self.value. When Python sees self.X it looks if there's a property X in your object, and if there is none, it looks at its class. Since you never set self.list_value, it's accessing the class variable, that is shared among all instances, so any modifiations will reflect in every other object.

Upvotes: 24

Aaron Dufour
Aaron Dufour

Reputation: 17505

The key difference is that you are appending to list_value, and you are assigning to value. They are called "class variables". Each instance has its own reference to the class variable, which is why the list is shared. However, when you assign, you are changing that instance's reference to point to a different variable, which explains the behavior of value.

If you are looking for instance variable behavior from list_value, initialize it in the constructor (a class method called __init__) instead.

Upvotes: 3

Related Questions