Changing a list derived from a reference list also changes the reference list?



  • a = 1
    b = [(a, a), (a + 1, a + 1)]
    
    d = 1
    g = b
    print('original:', b, 'new, pending:', g)
    c = [0, 1]
    for n in c:
        g[n] = (g[n][0] - d, g[n][1] - d)
    print('original:', b, 'new:', g)
    

    returns:

    original: [(1, 1), (2, 2)] new, pending: [(1, 1), (2, 2)]
    original: [(0, 0), (1, 1)] new: [(0, 0), (1, 1)]
    

    What is going on here? Why does changing g also change b?



  • hello @MauriceMeilleur,

    assigning a list to a new variable does not create a new list, just a new reference to the same list. (this also applies to dictionaries; both are mutable object types.)

    there are different ways to create a copy of a list:

    A = [1, 2, 3]
    B = A.copy() # or list(A) # or A[:]
    B.append(4)
    print(A)
    print(B)
    

    cheers!



  • @gferreira Thanks, Gustavo! I don't know how I've managed to go nearly four years without knowing this—I feel like I've used this method in the past to restore a reference. Lesson learned.


  • admin

    g is just a reference to the same object. You need to create a copy to get a new object with the same content.

    import copy
    
    a = 1
    b = [(a, a), (a + 1, a + 1)]
    print(id(b))
    
    g = b
    print(id(g))
    
    g = copy.deepcopy(b)
    print(id(g))
    

Log in to reply