python中不同形狀的數組的基本乘法

[英]Elementwise multiplication of arrays of different shapes in python


Say I have two arrays a and b,

假設有兩個數組a和b,

  a.shape = (5,2,3)
  b.shape = (2,3)

then c = a * b will give me an array c of shape (5,2,3) with c[i,j,k] = a[i,j,k]*b[j,k].

那么c = a *b會給我一個形狀為c(5,2,3)的數組,c[i,j,k] = a[i,j,k]*b[j,k]。

Now the situation is,

現在的情況是,

  a.shape = (5,2,3)
  b.shape = (2,3,8)

and I want c to have a shape (5,2,3,8) with c[i,j,k,l] = a[i,j,k]*b[j,k,l].

我想讓c有一個形狀(5,2,3,8)c[I,j,k,l] = a[I,j,k]*b[j,k,l]

How to do this efficiently? My a and b are actually quite large.

如何有效地做到這一點?我的a和b實際上很大。

2 个解决方案

#1


13  

This should work:

這應該工作:

a[..., numpy.newaxis] * b[numpy.newaxis, ...]

Usage:

用法:

In : a = numpy.random.randn(5,2,3)

In : b = numpy.random.randn(2,3,8)

In : c = a[..., numpy.newaxis]*b[numpy.newaxis, ...]

In : c.shape
Out: (5, 2, 3, 8)

Ref: Array Broadcasting in numpy

Ref: numpy中的數組廣播

Edit: Updated reference URL

編輯:更新引用URL

#2


7  

I think the following should work:

我認為以下方法應該有效:

import numpy as np
a = np.random.normal(size=(5,2,3))
b = np.random.normal(size=(2,3,8))
c = np.einsum('ijk,jkl->ijkl',a,b)

and:

和:

In [5]: c.shape
Out[5]: (5, 2, 3, 8)

In [6]: a[0,0,1]*b[0,1,2]
Out[6]: -0.041308376453821738

In [7]: c[0,0,1,2]
Out[7]: -0.041308376453821738

np.einsum can be a bit tricky to use, but is quite powerful for these sort of indexing problems:

np。einsum的使用可能有點棘手,但對於這類索引問題卻非常強大:

http://docs.scipy.org/doc/numpy/reference/generated/numpy.einsum.html

http://docs.scipy.org/doc/numpy/reference/generated/numpy.einsum.html

Also note that this requires numpy >= v1.6.0

還要注意,這需要numpy >= v1.6.0

I'm not sure about efficiency for your particular problem, but if it doesn't perform as well as needed, definitely look into using Cython with explicit for loops, and possibly parallelize it using prange

我不確定您的特定問題的效率,但是如果它的性能不如需要的那么好,一定要考慮使用Cython顯式for循環,並可能使用prange將其並行化

UPDATE

更新

In [18]: %timeit np.einsum('ijk,jkl->ijkl',a,b)
100000 loops, best of 3: 4.78 us per loop

In [19]: %timeit a[..., np.newaxis]*b[np.newaxis, ...]
100000 loops, best of 3: 12.2 us per loop


In [20]: a = np.random.normal(size=(50,20,30))
In [21]: b = np.random.normal(size=(20,30,80))

In [22]: %timeit np.einsum('ijk,jkl->ijkl',a,b)
100 loops, best of 3: 16.6 ms per loop

In [23]: %timeit a[..., np.newaxis]*b[np.newaxis, ...]
100 loops, best of 3: 16.6 ms per loop

In [2]: a = np.random.normal(size=(500,20,30))
In [3]: b = np.random.normal(size=(20,30,800))

In [4]: %timeit np.einsum('ijk,jkl->ijkl',a,b)
1 loops, best of 3: 3.31 s per loop

In [5]: %timeit a[..., np.newaxis]*b[np.newaxis, ...]
1 loops, best of 3: 2.6 s per loop

注意!

本站翻译的文章,版权归属于本站,未经许可禁止转摘,转摘请注明本文地址:https://www.itdaan.com/blog/2012/05/20/7202a9de20081c9771df17be0d29b36b.html



 
粤ICP备14056181号  © 2014-2020 ITdaan.com