1

I am at the moment of understanding how lists and while loops work in Python. Unfortunately, I am a bit confused with my code.

main_list = []
list_1 = [1, 2]
list_2 = [3, 4]

i = 0
n = 2

while i != n:

    number = int(input("Insert a number: "))

    list_1.append(number)
    main_list.append(list_1)
    main_list.append(list_2)

    i += 1

print(main_list)

Why am I getting an output of this,

>> Insert a number: 2
>> Insert a number: 3
>> [[1, 2, 2, 3], [3, 4], [1, 2, 2, 3], [3, 4]]

instead of this?

>> Insert a number: 2
>> Insert a number: 3
>> [[1, 2, 2], [3, 4], [1, 2, 2, 3], [3, 4]]

I would appreciate if anyone can explain it to me, thank you.

  • I think it changes the list every where where there is a reference of that list –  Aug 07 '21 at 10:41
  • 1
    `main_list` contains `list_1` and `list_2` twice each because that is what you put in it. `list_1` is `[1,2,2,3]` because that is what you put in it. – khelwood Aug 07 '21 at 10:43
  • 1
    You could also run this in http://www.pythontutor.com/ to see each step running visually. – Daniel Hao Aug 07 '21 at 10:57

4 Answers4

1

You are adding the list1 to main_list. So a reference of the list1 is stored there. So when you change the list1, it changes the list every where.

You can create a copy of the list before adding it to the list

main_list = []
list_1 = [1, 2]
list_2 = [3, 4]

i = 0
n = 2

while i != n:

    number = int(input("Insert a number: "))

    list_1.append(number)
    main_list.append(list_1.copy())
    main_list.append(list_2)

    i += 1

print(main_list)
0

The reason is that main_list contains references to list_1 and list_2 and NOT copies of them. To see this clearly add the following lines to the bottom of your code,

list_1.append(10)

print(main_list)

You will now get the following output,

[[1, 2, 2, 3], [3, 4], [1, 2, 2, 3], [3, 4]]
[[1, 2, 2, 3, 10], [3, 4], [1, 2, 2, 3, 10], [3, 4]]

To stop ths behavior you have to explicitly make copies of the lists using the copy library,

import copy

main_list = []
list_1 = [1, 2]
list_2 = [3, 4]

i = 0
n = 2

while i != n:

    number = int(input("Insert a number: "))

    list_1.append(number)
    main_list.append(copy.copy(list_1))
    main_list.append(copy.copy(list_2))

    i += 1

print(main_list)

Now your output is what you were after in the first place,

[[1, 2, 2], [3, 4], [1, 2, 2, 3], [3, 4]]
DrBwts
  • 3,470
  • 6
  • 38
  • 62
  • @JuventiusKriswijanarko if this helped you click the up button or click the tick or click both so other users can see which answers helped. – DrBwts Aug 07 '21 at 11:02
0

That's because you are modifying list_1 inside the while loop and appending it to main_list. But when you append, only the reference of list_1 is added to main_list.

Now at the end list_1 contents are [1,2,2,3]. And since main_list contains a reference to list_1, main_list shows the current contents of list_1 which is [1,2,2,3].

To avoid this, you have to append the contents of list_1 and not the reference to main_list. There are many ways to do it.

One of which is,

main_list.append(list(list_1))

Change your existing line to this.

Please read this - Shallow vs Deep Copy

Ram
  • 4,724
  • 2
  • 14
  • 22
0

Your Code:

main_list = []
list_1 = [1, 2]
list_2 = [3, 4]
i = 0
n = 2
while i != n:

    number = int(input("Insert a number: "))   
    list_1.append(number)    
    main_list.append(list_1)    
    main_list.append(list_2)    
    i += 1

print(main_list)

After 1st iteration:

main_list = [[1,2,2],[3,4]]
list_1 = [1, 2, 2]
list_2 = [3, 4]

After 2nd iteration:

main_list = [[1,2,2,3],[3,4], [1,2,2,3],[3,4]]
list_1 = [1, 2, 2,3]
list_2 = [3, 4]

what needs to be considered is: Under the hood python has REFERENCE_TYPE so basically what your main_list has is something like:

main_list= [
[reference_of_list1],[reference_of_list2],
[reference_of_list1],[reference_of_list2]]

so that could be a reason for the issue you're facing.

Dharman
  • 30,962
  • 25
  • 85
  • 135
Waleed J.
  • 47
  • 1
  • 6