Numpy multiply arrays into matrix (outer product)

2020-01-29 02:36发布

问题:

I have 2 numpy arrays of shape (5,1) say: a=[1,2,3,4,5] b=[2,4,2,3,6]

How can I make a matrix multiplying each i-th element with each j-th? Like:

..a = [1,2,3,4,5]
b 
2    2, 4, 6, 8,10
4    4, 8,12,16,20
2    2, 4, 6, 8,10
3    3, 6, 9,12,15
6    6,12,18,24,30

Without using forloops? is there any combination of reshape, reductions or multiplications that I can use?

Right now I create a a*b tiling of each array along rows and along colums and then multiply element wise, but it seems to me there must be an easier way.

回答1:

With numpy.outer() and numpy.transpose() routines:

import numpy as np

a = [1,2,3,4,5]
b = [2,4,2,3,6]
c = np.outer(a,b).transpose()

print(c)

Or just with swapped array order:

c = np.outer(b, a)

The output;

[[ 2  4  6  8 10]
 [ 4  8 12 16 20]
 [ 2  4  6  8 10]
 [ 3  6  9 12 15]
 [ 6 12 18 24 30]]


回答2:

For some reason np.multiply.outer seems to be faster than np.outer for small inputs. And broadcasting is faster still - but for bigger arrays they are all pretty much equal.

%timeit np.outer(a,b)
%timeit np.multiply.outer(a,b)
%timeit a[:, None]*b

100000 loops, best of 3: 5.97 µs per loop
100000 loops, best of 3: 3.27 µs per loop
1000000 loops, best of 3: 1.38 µs per loop

a = np.random.randint(0,10,100)
b = np.random.randint(0,10,100)

%timeit np.outer(a,b)
%timeit np.multiply.outer(a,b)
%timeit a[:, None]*b

100000 loops, best of 3: 15.5 µs per loop
100000 loops, best of 3: 14 µs per loop
100000 loops, best of 3: 13.5 µs per loop

a = np.random.randint(0,10,10000)
b = np.random.randint(0,10,10000)

%timeit np.outer(a,b)
%timeit np.multiply.outer(a,b)
%timeit a[:, None]*b

10 loops, best of 3: 154 ms per loop
10 loops, best of 3: 154 ms per loop
10 loops, best of 3: 152 ms per loop