Python: сумма всех перестановок внешних произведений числовых массивов массивов - PullRequest
0 голосов
/ 16 сентября 2018

У меня есть массив массивов Ai, и я хочу, чтобы каждый внешний продукт (np.outer (Ai [i], Ai [j])) суммировался с множителем масштабирования для получения H. Я могу пройти и сделать затем они объединяются с матрицей коэффициентов масштабирования. Я думаю, что все может быть значительно упрощено, но я не нашел общий / эффективный способ сделать это для ND. Как легче получить Arr2D и H? Примечание: Arr2D может быть 64 2D-массивами, а не 8x8 2D-массивами.

Ai = np.random.random((8,101))
Arr2D = np.zeros((Ai.shape[0], Ai.shape[0], Ai.shape[1], Ai.shape[1]))
Arr2D[:,:,:,:] = np.asarray([ np.outer(Ai[i], Ai[j]) for i in range(Ai.shape[0]) 
    for j in range(Ai.shape[0]) ]).reshape(Ai.shape[0],Ai.shape[0],Ai[0].size,Ai[0].size)
arr = np.random.random( (Ai.shape[0] * Ai.shape[0]) )
arr2D = arr.reshape(Ai.shape[0], Ai.shape[0])
H = np.tensordot(Arr2D, arr2D, axes=([0,1],[0,1]))

1 Ответ

0 голосов
/ 16 сентября 2018

Хорошая настройка для использования einsum!

np.einsum('ij,kl,ik->jl',Ai,Ai,arr2D,optimize=True)

Сроки -

In [71]: # Setup inputs
    ...: Ai = np.random.random((8,101))
    ...: arr = np.random.random( (Ai.shape[0] * Ai.shape[0]) )
    ...: arr2D = arr.reshape(Ai.shape[0], Ai.shape[0])

In [74]: %%timeit # Original soln
    ...: Arr2D = np.zeros((Ai.shape[0], Ai.shape[0], Ai.shape[1], Ai.shape[1]))
    ...: Arr2D[:,:,:,:] = np.asarray([ np.outer(Ai[i], Ai[j]) for i in range(Ai.shape[0]) 
    ...:     for j in range(Ai.shape[0]) ]).reshape(Ai.shape[0],Ai.shape[0],Ai[0].size,Ai[0].size)
    ...: H = np.tensordot(Arr2D, arr2D, axes=([0,1],[0,1]))
100 loops, best of 3: 4.5 ms per loop

In [75]: %timeit np.einsum('ij,kl,ik->jl',Ai,Ai,arr2D,optimize=True)
10000 loops, best of 3: 146 µs per loop

30x+ ускорение там!

...