np.matmul() și operatorul @ în NumPy

Algebră liniară NumPy 1.10+

Înmulțirea de matrice cu np.matmul sau operatorul @; diferența față de *, care înmulțește element cu element.

Sintaxă
np.matmul(a, b)
a @ b

Ce face np.matmul() și operatorul @

a @ b (operator din Python 3.5) este același lucru cu np.matmul(a, b): înmulțire de matrice. Elementul de pe rândul i și coloana j al rezultatului este produsul scalar dintre rândul i din a și coloana j din b. Numărul de coloane din a trebuie să fie egal cu numărul de rânduri din b.

Operatorul * face altceva: înmulțește elementele de pe aceeași poziție (și aplică broadcasting). Pentru două matrice 2×2 ambele operații merg, dar dau rezultate diferite, așa că greșeala nu se vede ca eroare.

Față de np.dot, @ nu acceptă scalari (pentru ei folosești *) și tratează tablourile cu 3 sau mai multe dimensiuni ca pe un set de matrice înmulțite separat.

Parametri

Parametru Descriere
a, b Tablouri cu cel puțin o dimensiune; ultima axă a lui a trebuie să aibă aceeași lungime ca penultima axă a lui b.

Ce returnează

Un tablou (sau un scalar pentru doi vectori 1D).

Exemple

Exemplul 1: @ față de *

import numpy as np

a = np.array([[1, 2], [3, 4]])
b = np.array([[5, 6], [7, 8]])

print("a @ b:")
print(a @ b)
print("a * b:")
print(a * b)
print(np.array_equal(a @ b, np.matmul(a, b)))

Rezultat

a @ b:
[[19 22]
 [43 50]]
a * b:
[[ 5 12]
 [21 32]]
True

Exemplul 2: Forme diferite

Din (2, 3) @ (3, 2) rezultă (2, 2). A.T este transpusa.

import numpy as np

A = np.array([[1, 0, 2], [0, 3, 1]])
B = np.array([[1, 2], [0, 1], [4, 0]])
print((A @ B).shape)
print(A @ B)
print((A @ A.T).shape)

try:
    A @ A
except ValueError as e:
    print("Eroare:", type(e).__name__)

Rezultat

(2, 2)
[[9 2]
 [4 3]]
(2, 2)
Eroare: ValueError

Exemplul 3: Prețuri în lei și euro pentru mai multe coșuri

Fiecare rând din cosuri sunt cantitățile; coloanele din preturi sunt prețul în lei și în euro.

import numpy as np

cosuri = np.array([
    [2, 1, 0],   # coșul Anei
    [1, 3, 2],   # coșul lui Mihai
])
preturi = np.array([
    [4.5, 0.9],
    [7.0, 1.4],
    [12.0, 2.4],
])
print(cosuri @ preturi)

Rezultat

[[16.   3.2]
 [49.5  9.9]]

Greșeli frecvente

  • Scrii a * b și crezi că ai înmulțit matrice. * înmulțește element cu element; pentru matrice folosește @.
  • Încerci a @ 2: matmul nu acceptă scalari și dă ValueError. Pentru înmulțirea cu un număr folosește a * 2.
  • Înmulțești matrice cu forme (2, 3) și (2, 3) și primești ValueError. Verifică formele; de multe ori ai nevoie de transpusa b.T.

Comenzi înrudite

  • np.dot(): Calculează produsul scalar a doi vectori sau produsul matriceal a două matrice.
  • Operații element cu element și ufunc-uri: Operatorii aritmetici și funcțiile matematice NumPy (ufunc-uri) se aplică pe fiecare element, fără bucle.
  • np.linalg.inv(): Calculează inversa unei matrice pătrate; pentru o matrice singulară aruncă LinAlgError.
  • Broadcasting: Regulile prin care NumPy face operații între tablouri de forme diferite, de exemplu o matrice și un rând sau un scalar.