6.8. Operátory

Prvním druhem matematiky, kterou numpy provádí nad ndarray, jsou standardní operátory Pythonu. Aritmetické, porovnávací i bitové operátory všechny pracují po prvcích – každý operátor projde pole (nebo obě pole) jednou od začátku do konce v rámci jediného volání knihovny, mnohem rychleji než ekvivalentní Python cyklus for.

6.8.1. Aritmetika

+, -, *, /, //, %, ** všechny fungují mezi dvěma poli kompatibilního tvaru nebo mezi polem a skalárem:

a = np.array([1, 2, 3, 4], dtype=np.float)
b = np.array([10, 20, 30, 40], dtype=np.float)

print(a + b)        # array([11.0, 22.0, 33.0, 44.0])
print(a * 2)        # array([2.0, 4.0, 6.0, 8.0])
print(b - a)        # array([9.0, 18.0, 27.0, 36.0])
print(b / a)        # array([10.0, 10.0, 10.0, 10.0])

Výsledný dtype se řídí pravidly rozšiřování typu (upcasting) popsanými v Dtypy. Celočíselná pole se při přetečení zalomí; když na tom záleží, přetypujte před operací na širší dtype.

Operátor maticového násobení @ není implementován. Pro maticové / vektorové součiny použijte dot().

6.8.1.1. Formy na místě (in-place)

Každý aritmetický operátor má formu na místě (in-place) – +=, -=, *=, /=, %=, **=. Forma na místě zapisuje přes stávající buffer namísto alokace dočasného:

b = b + 1            # allocates a temporary the size of b
b += 1               # no temporary

Na mikrokontroléru je druhá forma v podstatě povinná pro každou výkonově kritickou smyčku.

6.8.2. Bitové operace

Bitové operátory &, |, ^ pracují po prvcích na celočíselných polích. Při aplikaci na pole float nebo complex vyvolají TypeError

a = np.array([0b1100, 0b1010], dtype=np.uint8)
b = np.array([0b1010, 0b1100], dtype=np.uint8)
print(a & b)        # array([8, 8], dtype=uint8)
print(a | b)        # array([14, 14], dtype=uint8)
print(a ^ b)        # array([6, 6], dtype=uint8)

Unární ~ provádí bitovou negaci NOT na celočíselném poli.

Operátory posunu << a >> nejsou zapojeny na úrovni operátorů Pythonu. Funkční formy left_shift() a right_shift() fungují:

np.left_shift(a, 2)
np.right_shift(b, 1)

6.8.3. Porovnávání

==, !=, <, <=, >, >= všechny vracejí ndarray typu bool o broadcastovaném tvaru:

a = np.array([1, 2, 3, 4, 5], dtype=np.uint8)
print(a < 3)
# array([True, True, False, False, False], dtype=bool)

Booleovský výsledek je přesně to, co konzumují indexování a Výběr a přeuspořádání.

6.8.3.1. Pravidlo strany

ndarray musí být při porovnávání se skalárem na levé straně relačního operátoru. a > 2 funguje; 2 < a vyvolá TypeError. Pro symetrickou formu použijte názvy funkcí:

np.greater(5, a)        # 5 > a, element-wise
np.less(5, a)           # 5 < a, element-wise
np.equal(5, a)          # 5 == a, element-wise
np.not_equal(5, a)      # 5 != a, element-wise

6.8.4. Unární operátory

  • +a – vrací kopii pole.

  • -a – negace. Na bezznaménkových dtype se hodnoty zalomí modulo \(2^N\), stejně jako u binárních operátorů.

  • abs(a) – absolutní hodnota po prvcích. Na bezznaménkových dtype vrací kopii bez výpočtu.

  • ~a – bitová inverze (pouze celočíselná pole).

  • len(a) – vrací délku první osy, v souladu s konvencí sekvencí Pythonu.

6.8.5. Co chybí

Pravostranné operátory pro porovnávání a některé bitové operace nejsou implementovány stejným způsobem jako aritmetické operátory. Když by ndarray měl skončit na pravé straně, použijte funkční formy (výše).

Úplný seznam podporovaných operátorů a rozšiřování typu (upcasting), které dodržují, najdete v numpy — operace s poli kompatibilní s numpy.