Логическая адресация, шалость неразбериха с другими матрицами

Я только что обнаружил проблему и не знаю, так ли это, или я просто делаю это неправильно. Когда я использую логическую адресацию в простой матрице, чтобы изменить все значения матрицы, скажем, равные 1. Все другие матрицы, которые так или иначе имеют отношение к этой матрице, также будут изменены.

In [1]: import numpy as np
In [2]: from numpy import matrix as mtx
In [3]: A=mtx(np.eye(6))
In [4]: A
Out[4]: 
matrix([[ 1.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  1.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  1.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  1.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  1.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  1.]])

In [5]: B=A

In [6]: C=B

In [7]: D=C

In [8]: A[A==1]=5

In [9]: A
Out[9]: 
matrix([[ 5.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  5.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  5.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  5.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  5.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  5.]])

In [10]: B
Out[10]: 
matrix([[ 5.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  5.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  5.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  5.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  5.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  5.]])

In [11]: C
Out[11]: 
matrix([[ 5.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  5.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  5.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  5.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  5.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  5.]])

In [12]: D
Out[12]: 
matrix([[ 5.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  5.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  5.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  5.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  5.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  5.]])

Может кто-нибудь сказать мне, что я делаю не так? это ошибка?

1 ответ

Решение

Это не ошибка. поговорка B=A в питоне означает, что оба B а также A указать на тот же объект. Вам нужно скопировать матрицу.

>>> import numpy as np
>>> from numpy import matrix as mtx
>>> A = mtx(np.eye(6))
>>> B = A.copy()
>>> C = A

#Check memory locations.
>>> id(A)
19608352
>>> id(C)
19608352    #Same object as A
>>> id(B)
19607992    #Different object then A

>>> A[A==1] = 5
>>> B   #B is a different object then A
matrix([[ 1.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  1.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  1.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  1.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  1.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  1.]])

>>> C   #C is the same object as A
matrix([[ 5.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  5.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  5.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  5.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  5.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  5.]])

Та же самая проблема может быть замечена со списком python:

>>> A = [5,3]
>>> B = A
>>> B[0] = 10
>>> A
[10, 3]

Обратите внимание, что это отличается от возврата пустого представления, как в этом случае:

>>> A = mtx(np.eye(6))
>>> B = A[0]  #B is a view and now points to the first row of A

>>> id(A)
28088720
>>> id(B)  #Different objects!
28087568  
#B still points to the memory location of A's first row, but through numpy trickery

>>> B
matrix([[ 1.,  0.,  0.,  0.,  0.,  0.]])
>>> B *= 5 #In place multiplication, updates B which is the same as A's first row
>>> A
matrix([[ 5.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  1.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  1.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  1.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  1.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  1.]])

Как мнение B указывает на первый ряд A, A изменено Теперь давайте заставим копию.

>>> B = B*10 #Assigns B*10 to a different chunk of memory
>>> A
matrix([[ 5.,  0.,  0.,  0.,  0.,  0.],
        [ 0.,  1.,  0.,  0.,  0.,  0.],
        [ 0.,  0.,  1.,  0.,  0.,  0.],
        [ 0.,  0.,  0.,  1.,  0.,  0.],
        [ 0.,  0.,  0.,  0.,  1.,  0.],
        [ 0.,  0.,  0.,  0.,  0.,  1.]])
>>> B
matrix([[ 50.,   0.,   0.,   0.,   0.,   0.]])
Другие вопросы по тегам