Numpy divide a lo largo del eje
vector (2)
¿Existe una función numpy para dividir una matriz a lo largo de un eje con elementos de otra matriz? Por ejemplo, supongamos que tengo una matriz a con forma (l, m, n) y una matriz b con forma (m,); Estoy buscando algo equivalente a:
def divide_along_axis(a,b,axis=None):
if axis is None:
return a/b
c = a.copy()
for i, x in enumerate(c.swapaxes(0,axis)):
x /= b[i]
return c
Por ejemplo, esto es útil cuando se normaliza una matriz de vectores:
>>> a = np.random.randn(4,3)
array([[ 1.03116167, -0.60862215, -0.29191449],
[-1.27040355, 1.9943905 , 1.13515384],
[-0.47916874, 0.05495749, -0.58450632],
[ 2.08792161, -1.35591814, -0.9900364 ]])
>>> np.apply_along_axis(np.linalg.norm,1,a)
array([ 1.23244853, 2.62299312, 0.75780647, 2.67919815])
>>> c = divide_along_axis(a,np.apply_along_axis(np.linalg.norm,1,a),0)
>>> np.apply_along_axis(np.linalg.norm,1,c)
array([ 1., 1., 1., 1.])
Creo que puedes obtener este comportamiento con el comportamiento de transmisión habitual de numpy:
In [9]: a = np.array([[1., 2.], [3., 4.]])
In [10]: a / np.sum(a, axis=0)
Out[10]:
array([[ 0.25 , 0.33333333],
[ 0.75 , 0.66666667]])
Si lo he interpretado correctamente.
Si quieres el otro eje puedes transponer todo:
> a = np.random.randn(4,3).transpose()
> norms = np.apply_along_axis(np.linalg.norm,0,a)
> c = a / norms
> np.apply_along_axis(np.linalg.norm,0,c)
array([ 1., 1., 1., 1.])
Para el ejemplo específico que has dado: dividiendo una matriz (l, m, n) por (m,) puedes usar np.newaxis:
a = np.arange(1,61, dtype=float).reshape((3,4,5)) # Create a 3d array
a.shape # (3,4,5)
b = np.array([1.0, 2.0, 3.0, 4.0]) # Create a 1-d array
b.shape # (4,)
a / b # Gives a ValueError
a / b[:, np.newaxis] # The result you want
Puedes leer todo sobre las reglas de transmisión here . También puede usar newaxis más de una vez si es necesario. (por ejemplo, para dividir una matriz de formas (3,4,5,6) por una matriz de formas (3,5)).
Desde mi entendimiento de los documentos, el uso de newaxis + broadcasting evita también cualquier copia de matriz innecesaria.
Indexación, newaxis, etc. se describen más detalladamente here ahora. (Documentación reorganizada desde esta respuesta publicada por primera vez).