Weighted average by 4 times with a 2D array of weights without regard to the list
(This question is similar to Numpy averaging with multidimensional weights along the axis , but more complicated.)
I have a numpy array, d
, d.shape=(16,3,90,144)
and an array of numpy weights e
, e.shape=(16,3)
. I want to take a weighted average a
along axis 1 using e
. So the output should be a numpy array with shape (16,90,144)
. I can accomplish this with a list comprehension:
np.array([np.average(d[n], weights=e[n], axis=0) for n in range(16)])
But like the previous question, I would like to avoid converting from a list back to a numpy array. This case is more complicated than the previous question because the weights are not the same every time (i.e. weights=e[n]
, not weights=b
).
Can anyone please help? Thank!
source to share
It would be nice to use np.average
directly. However, for this, d
both the weights e
must have the same shape, and for you, the broadcast will be implicitly here.
Explicit translation e
(with np.broadcast_arrays
), so it has the same shape as d
, but it is a waste of memory. So instead one could look into the source code defining numpy.average , and try to reproduce the calculation:
In [121]: d = np.random.random((16,3,90,144))
In [122]: e = np.random.random((16,3))
In [123]: f = e[:,:,None,None]
In [124]: scl = f.sum(axis = 1)
In [125]: avg = np.multiply(d,f).sum(axis = 1)/scl
Here is a check that the calculation returns the same result as a list comprehension:
In [126]: avg_lc = np.array([np.average(d[n], weights=e[n], axis=0) for n in range(d.shape[0])])
In [127]: np.allclose(avg, avg_lc)
Out[127]: True
source to share