# In Python, why my variable StartingU get updated when I only update the variable AverageU in my for loops? What is wrong with the code?

The purpose is to calculate the average value (AverageU) from a starting array (StartingU)

```import numpy as np

AverageU=np.zeros((3,3))
StartingU=np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])

size=2
stride=1
m, n = StartingU.shape

print("Before averaging:")
print("AverageU=", AverageU)
print("StartingU=", StartingU)

AverageU = StartingU
```

The for loops that calculate the average values for AverageU

```for i in range(0, m - size + 1, stride):
for j in range(0, n - size + 1, stride):
avg = np.sum(np.sum(AverageU[i:i + size, j:j + size])) / (size * size)
for ii in range(i, i + size):
for jj in range(j, j + size):
AverageU[ii, jj] = avg
#print("In for loop, StartingU=", StartingU)

print("After averaging:")
print("AverageU=", AverageU)
print("StartingU=", StartingU)
```

Output:

```Before averaging:
AverageU= [[0. 0. 0.]
[0. 0. 0.]
[0. 0. 0.]]
StartingU= [[1 2 3]
[4 5 6]
[7 8 9]]
After averaging:
AverageU= [[3 3 3]
[5 5 5]
[5 5 5]]
StartingU= [[3 3 3]
[5 5 5]
[5 5 5]]
```

The problem is why StartingU gets updated? It should be unchanged

```StartingU=np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
```

AverageU changed since this code, not after for loop.

```print("Before averaging:")
print("AverageU=", AverageU)
print("StartingU=", StartingU)

AverageU = StartingU  # since here, AverageU variable changed

print("AverageU=", AverageU)
print("StartingU=", StartingU)  # please check here again.
```

AverageU and StartingU are the same instances. You can check it with is function.

```StartingU = np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])
AverageU = StartingU
print(StartingU is AverageU)  # True
```

You should make a new instance as the comment said.

```StartingU = np.array([[1, 2, 3], [4, 5, 6], [7, 8, 9]])

AverageU_new1 = StartingU[:]
AverageU_new2 = StartingU.copy()
print(StartingU is AverageU_new2)  # False
print(StartingU is AverageU_new1)  # False
```

AverageU = StartingU This code just makes another reference to the same object with a new name and this indicates the same memory. You can check the memory address of the variable with function id

You can compare like this.

```copy_1 = StartingU
copy_2 = StartingU[:]
copy_3 = StartingU.copy()
print(id(StartingU), id(copy_1), id(copy_2), id(copy_3))
```

Notice

Copy with the colon is actually a shallow copy, it copies only the reference of the nested list.

6 People found this is helpful