Изменение диагонального массива np.diag с помощью цикла - PullRequest
1 голос
/ 19 июня 2020

Я пытался посмотреть, как работает np.diag_indices, и найти их примеры, однако документация по нему немного светлая. Я знаю, что это создает диагональный массив через вашу матрицу, однако я хочу изменить диагональный массив (я думал об использовании al oop, чтобы изменить его размеры или что-то в этом роде).

IE говорит, что у нас есть матрица 3x2:

[[1 2]
 [3 4]
 [5  6]]

Теперь, если я использую np.diag_indices, он сформирует диагональный массив, начинающийся с (0,0) и проходящий через (1,1 ).

[1 4]

Однако я бы хотел, чтобы этот диагональный массив затем сдвинулся на единицу вниз. Итак, теперь он начинается с (0,1) и проходит через (1,2).

[3 6]

Однако для np.diag_indices есть только 2 аргумента, ни один из которых, судя по всему, не позволяет мне это сделать. Я использую неправильный инструмент, чтобы добиться этого? Если да, то какие инструменты я могу использовать для создания изменяющегося диагонального массива, проходящего через мою матрицу? (Я ищу что-то, что также будет работать с более крупными матрицами, такими как 200x50).

1 Ответ

3 голосов
/ 19 июня 2020

Код для diag_indices прост, настолько прост, что я никогда его не использовал:

idx = arange(n)
return (idx,) * ndim

In [68]: np.diag_indices(4,2)                                                   
Out[68]: (array([0, 1, 2, 3]), array([0, 1, 2, 3]))

Он просто возвращает кортеж массивов, arange повторяется n раз. Это полезно для индексации главной диагонали квадратной матрицы, например

In [69]: arr = np.arange(16).reshape(4,4)                                       
In [70]: arr                                                                    
Out[70]: 
array([[ 0,  1,  2,  3],
       [ 4,  5,  6,  7],
       [ 8,  9, 10, 11],
       [12, 13, 14, 15]])
In [71]: arr[np.diag_indices(4,2)]                                              
Out[71]: array([ 0,  5, 10, 15])

Приложение представляет собой прямую индексацию с двумя массивами, которые совпадают по форме.

Это работает с другими формами - если они большие enogh.

np.diag, примененный к тому же массиву, делает то же самое:

In [72]: np.diag(arr)                                                           
Out[72]: array([ 0,  5, 10, 15])

, но также позволяет смещение:

In [73]: np.diag(arr, 1)                                                        
Out[73]: array([ 1,  6, 11])

== =

Индексирование с помощью diag_indices действительно позволяет нам изменить эту диагональ:

In [78]: arr[np.diag_indices(4,2)] += 10                                        
In [79]: arr                                                                    
Out[79]: 
array([[10,  1,  2,  3],
       [ 4, 15,  6,  7],
       [ 8,  9, 20, 11],
       [12, 13, 14, 25]])

====

Но нам необязательно использовать diag_indices для генерации желаемых массивов индексации:

In [80]: arr = np.arange(1,7).reshape(3,2)                                      
In [81]: arr                                                                    
Out[81]: 
array([[1, 2],
       [3, 4],
       [5, 6]])

выбор значений из первых 2 строк и столбцов:

In [82]: arr[np.arange(2), np.arange(2)]                                        
Out[82]: array([1, 4])
In [83]: arr[np.arange(2), np.arange(2)] += 10                                  
In [84]: arr                                                                    
Out[84]: 
array([[11,  2],
       [ 3, 14],
       [ 5,  6]])

и для разностного выбора строк:

In [85]: arr[np.arange(1,3), np.arange(2)] += 20                                
In [86]: arr                                                                    
Out[86]: 
array([[11,  2],
       [23, 14],
       [ 5, 26]])

Соответствующий раздел документации по advanced indexing с целочисленными массивами: https://numpy.org/doc/stable/reference/arrays.indexing.html#purely -integer-array-indexing

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...