Class variables behave differently for list and int?

python, python-2.7

Solution

x.a.append(1)

changes the class attribute `c.a`, a `list`, by calling its `append` method, which modifies the list in-place.

x.b += 1

is actually a shorthand for

x.b = x.b + 1

because integers in Python are immutable, so they don't have an `__iadd__` (in-place add) method. The result of this assignment is to set an attribute `b` on the instance `x`, with value `2` (the result of evaluating the right-hand side of the assignment). This new instance attribute shadows the class attribute.

To see the difference between an in-place operation and an assignment, try

x.a += [1]

and

x.a = x.a + [1]

These will have different behavior.

EDIT The same functionality can be obtained for integers by boxing them:

class HasABoxedInt(object):
    boxed_int = [0]    # int boxed in a singleton list

a = HasABoxedInt()
a.boxed_int[0] += 1
b = HasABoxedInt()
print(b.boxed_int[0])  # prints 1, not zero

or

class BoxedInt(object):
    def __init__(self, value):
        self.value = value
    def __iadd__(self, i):
        self.value += i

Problem

The class shared variables are shared with all the instances of the classes as far as I know. But I am having trouble getting my head around this. ``` class c(): a=[1] b=1 def __init__(self): pass x=c() x.a.append(1) x.b+=1 #or x.b=2 print x.a #[1,1] print x.b #2 y=c() print y.a #[1,1] :As Expected print y.b #1 :why not 2? ``` y.a resonates with the x.a but y.b doesn't. hope someone can clarify. EDIT: And how can the same functionality be created for ints.

Original source