Neničelni elementi

numpy je zanimiv modul, ker ima precej funkcij, ki utegnejo izgledati nenavadne, v resnici pa so resno uporabne. Tipičen primer je np.nonzero, ki vrne indekse neničelnih elementov.

import numpy as np

a = np.array([5, 0, 1, 2, 0])
np.nonzero(a)
(array([0, 2, 3]),)

Zakaj je vrnil terko z enim elementom? Ker pač vedno vrne terko, elementov v njej pa je toliko, kolikor je dimenzij. Če funkciji nonzero podamo dvodimenzionalno tabelo, vrne terko z dvema tabelama. Prva vsebuje indekse po prvi osi, druga po drugi.

a = np.array([[5, 8, 0],
              [0, 1, 2],
              [1, 0, 3]])

np.nonzero(a)
(array([0, 0, 1, 1, 2, 2]), array([0, 1, 1, 2, 0, 2]))

To je videti hecno, ampak to so točno indeksi, ki jih potrebujemo, da preberemo te elemente.

x, y = np.nonzero(a)
a[x, y]
array([5, 8, 1, 2, 1, 3])

Ker je par indeksov v resnici terka, gre celo tako.

a[np.nonzero(a)]
array([5, 8, 1, 2, 1, 3])

Še vedno je videti precej brez zveze. Zakaj bi nas tako zelo zanimali neničelni elementi? Navadno nas res ne, znajo pa nas zanimati neničelni elementi matrike bool-ov. To so elementi, ki ustrezajo določenemu pogoju. Tole, recimo, so indeksi vseh elementov večjih od 1.

np.nonzero(a > 1)
(array([0, 0, 1, 2]), array([0, 1, 2, 2]))

Naloga

Za konec se spodobi reševati zadnjo nalogo, 25, Sea Cucumber.

Najprej nekaj, o čemer doslej nismo posebej govorili: tabele lahko vsebujejo tudi nize. Jaz sem si pri reševanju te naloge pripravil tabelico, katere elementi so bili v resnici črke ., > in <.

Zdaj pa nasveti. V vsakem koraku ugotovite koordinate vseh >. Pripravite koordinate desno od njih. Nato pripravite masko, ki pove, za katere od njih so koordinate desno od njih (z modulom po deljenju s širino, da skočimo z desnega roba na levega) proste. S temi koordinatami in masko potem spraznite trenutna polja in nastanite nove. Isto ponovite za v; če se znajdete, bo to kar v zanki čez ">v". Vse skupaj ponavljamo, dokler se uspe komu premikati.

Ni težko in po nalogi boste imeli dober občutek, da ste se nekaj naučili. Upam. :)