简体   繁体   中英

Multiply each column from 2D array with each column from another 2D array

I have two Numpy arrays x with shape (m, i) and y with shape (m, j) (so the number of rows is the same). I would like to multiply each column of x with each column of y element-wise so that the result is of shape (m, i*j) .

Example:

import numpy as np

np.random.seed(1)
x = np.random.randint(0, 2, (10, 3))
y = np.random.randint(0, 2, (10, 2))

This creates the following two arrays x :

array([[1, 1, 0],
       [0, 1, 1],
       [1, 1, 1],
       [0, 0, 1],
       [0, 1, 1],
       [0, 0, 1],
       [0, 0, 0],
       [1, 0, 0],
       [1, 0, 0],
       [0, 1, 0]])

and y :

array([[0, 0],
       [1, 1],
       [1, 1],
       [1, 0],
       [0, 0],
       [1, 1],
       [1, 1],
       [1, 1],
       [0, 1],
       [1, 0]])

Now the result should be:

array([[0, 0, 0, 0, 0, 0],
       [0, 0, 1, 1, 1, 1],
       [1, 1, 1, 1, 1, 1],
       [0, 0, 0, 0, 1, 0],
       [0, 0, 0, 0, 0, 0],
       [0, 0, 0, 0, 1, 1],
       [0, 0, 0, 0, 0, 0],
       [1, 1, 0, 0, 0, 0],
       [0, 1, 0, 0, 0, 0],
       [0, 0, 1, 0, 0, 0]])

Currently, I've implemented this operation with two nested loops over the columns of x and y :

def _mult(x, y):
    r = []
    for xc in x.T:
        for yc in y.T:
            r.append(xc * yc)
    return np.array(r).T

However, I'm pretty sure that there must be a more elegant solution that I can't seem to come up with.

Use NumPy broadcasting -

(y[:,None]*x[...,None]).reshape(x.shape[0],-1)

Explanation

As inputs, we have -

y : 10 x 2
x : 10 x 3

With y[:,None] , we are introducing a new axis between the existing two dims, thus creating a 3D array version of it. This keeps the first axis as the first one in 3D version and pushes out the second axis as the third one.

With x[...,None] , we are introducing a new axis as the last one by pushing up the two existing dims as the first two dims to result in a 3D array version.

To summarize, with the introduction of new axes, we have -

y : 10 x 1 x 2
x : 10 x 3 x 1

With y[:,None]*x[...,None] , there would be broadcasting for both y and x , resulting in an output array with a shape of (10,3,2) . To get to the final output array of shape (10,6) , we just need to merge the last two axes with that reshape.

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM