vectores - multiplicar dos matrices en python
Multiplica varias matrices en nĂºmeros. (5)
Supongamos que tiene n matrices cuadradas A1, ..., An. ¿Hay alguna forma de multiplicar estas matrices de una manera ordenada? Que yo sepa, dot in numpy solo acepta dos argumentos. Una forma obvia es definir una función para llamarse a sí misma y obtener el resultado. ¿Hay alguna mejor manera de hacerlo?
Esta podría ser una característica relativamente reciente, pero me gusta:
A.dot(B).dot(C)
o si tuvieras una cadena larga podrías hacer:
reduce(numpy.dot, [A1, A2, ..., An])
Actualizar:
Hay más información sobre reducir here. Aquí hay un ejemplo que podría ayudar.
>>> A = [np.random.random((5, 5)) for i in xrange(4)]
>>> product1 = A[0].dot(A[1]).dot(A[2]).dot(A[3])
>>> product2 = reduce(numpy.dot, A)
>>> numpy.all(product1 == product2)
True
Actualización 2016: a partir de Python 3.5, hay un nuevo símbolo matrix_multiply, @
:
R = A @ B @ C
Otra forma de lograr esto sería utilizando einsum
, que implementa la convención de suma de Einstein para NumPy.
Explicar brevemente esta convención con respecto a este problema: cuando anota su producto de matriz múltiple como una gran suma de productos, obtiene algo como:
P_im = sum_j sum_k sum_l A1_ij A2_jk A3_kl A4_lm
donde P
es el resultado de su producto y A1
, A2
, A3
y A4
son las matrices de entrada. Tenga en cuenta que suma exactamente esos índices que aparecen dos veces en el sumando, a saber, j
, k
y l
. Como una suma con esta propiedad a menudo aparece en la física, el cálculo vectorial y, probablemente, en algunos otros campos, existe una herramienta NumPy para esto, a saber, einsum
.
En el ejemplo anterior, puede usarlo para calcular su producto de matriz de la siguiente manera:
P = np.einsum( "ij,jk,kl,lm", A1, A2, A3, A4 )
Aquí, el primer argumento le dice a la función qué índices se aplican a las matrices de los argumentos y luego todos los índices que aparecen doblemente se suman, dando el resultado deseado.
Tenga en cuenta que la eficiencia computacional depende de varios factores (por lo que probablemente sea mejor que solo la pruebe):
- ¿Por qué ensum de numpy es más lento que las funciones integradas de numpy?
- ¿Por qué ensum de numpy es más rápido que las funciones integradas de numpy?
Resucitando una vieja pregunta con una actualización:
A partir del 13 de noviembre de 2014, ahora existe una función np.linalg.multi_dot
que hace exactamente lo que usted desea. También tiene la ventaja de optimizar el orden de las llamadas, aunque eso no es necesario en su caso.
Tenga en cuenta que esta disponible a partir de la versión numpy 1.10.
Si calcula todas las matrices a priori, debe utilizar un esquema de optimización para la multiplicación de la cadena de matrices. Vea este artículo de Wikipedia .
A_list = [np.random.randn(100, 100) for i in xrange(10)]
B = np.eye(A_list[0].shape[0])
for A in A_list:
B = np.dot(B, A)
C = reduce(np.dot, A_list)
assert(B == C)