Python 3, как использовать многопоточность с нормой ninaly linalg - PullRequest
0 голосов
/ 22 мая 2019

Я использую python3 с np.linalg.norm для вычисления норм для строк в матрице (норма (ось = 1)). Есть ли простой способ, используя только np для его запуска?используя многопоточность или многоядерность?

1 Ответ

1 голос
/ 22 мая 2019

Мы можем использовать numexpr модуль , который поддерживает многоядерную обработку, например: *

import numexpr as ne

def linalg_norm(a):
    sq_norm = ne.evaluate('sum(a**2,1)')
    return ne.evaluate('sqrt(sq_norm)')

Чтобы выполнить уменьшение нормы вдоль любой другой оси, замените 1 наномер этой оси в выражении вычисления - 'sum(a**2,1)'.

Пример выполнения -

In [34]: np.random.seed(0)
    ...: a = np.random.rand(4,5)

In [35]: np.linalg.norm(a,axis=1)
Out[35]: array([1.28545589, 1.57467272, 1.4460319 , 1.43656019])

In [36]: linalg_norm(a)
Out[36]: array([1.28545589, 1.57467272, 1.4460319 , 1.43656019])

Related post о том, как управлять многоядерными функциями.


Для полноты можно предложить несколько альтернатив.

Эффективное решение будет с np.einsum -

In [39]: np.sqrt(np.einsum('ij,ij->i',a, a))
Out[39]: array([1.28545589, 1.57467272, 1.4460319 , 1.43656019])

С np.matmul/@ operator on Python 3.x -

In [6]: np.sqrt(np.matmul(a[:,None],a[:,:,None])[:,0,0])
Out[6]: array([1.28545589, 1.57467272, 1.4460319 , 1.43656019])

In [7]: np.sqrt((a[:,None] @ a[:,:,None])[:,0,0])
Out[7]: array([1.28545589, 1.57467272, 1.4460319 , 1.43656019])
...