Institute of Computer Science
  1. Courses
  2. 2025/26 fall
  3. Computer Programming (LTAT.03.001)
ET
Log in

Computer Programming 2025/26 fall

  • Üldinfo
  • 1. Muutuja ja avaldis
  • 2. Tingimuslause
  • 3. Funktsioon
  • 4. Korduslause
  • 5. Sõned. Lihtsam failitöötlus
  • 6. Kontrolltöö 1
  • 7. Järjend
  • 8. Järjend 2
  • 9. Kahekordne tsükkel. Failitöötlus
  • 10. Andmestruktuurid
  • 11. Andmestruktuurid 2
  • 12. Kontrolltöö 2
  • 13. Objektorienteeritud programmeerimine
  • 14. Objektorienteeritud programmeerimine 2
  • 15. Rekursioon
  • 16. Kordamine. Projektide esitlused
  • Viiteid
  • Silmaringimaterjalid

Arhiveeritud esialgsed silmaringimaterjalid

  1. Standardteek ja moodulid
  2. Rakendusliidesed
  3. Regulaaravaldised
  4. Andmebaasid
  5. Veebirakenduste loomine
  6. Objektorienteeritud programmeerimine
  7. Graafiliste mängude loomine
  8. Keerulisemad Pythoni võimalused
  9. Võistlusprogrammeerimine
  10. Veebisisu parsimine
  11. Pilditöötlus
  12. Pythoni siseehitus
  13. Helitöötlus
  14. Kodeerimine ja krüpteerimine
  15. NumPy
  • Materjalid

NumPy massiivid

See peatükk keskendub teegile NumPy (Numerical Python). See on üks enimkasutatud Pythoni teek, mida tavaliselt kasutatakse suuremate andmehulkade töötlemiseks või teisendamiseks. Lisaks on sellega parem lahendada veidi keerulisemaid algebra ülesandeid kui mooduliga math. Sisseehitatud on näiteks vektor- ja maatriksarvutused. Peatükis selgitatakse NumPy tähtsaimaid mõisteid ja käske. Kõik pole mõeldud kohe pähe õppimiseks - võib ka orienteeruda lõigupealkirjade järgi ja kasutada peatükki spikrina!

Ettevalmistus

Selle peatüki mõistmiseks peaks õpikust olema läbitud järjendite peatükk. Kui sul pole veel paigaldatud teek numpy, tuleb seda nüüd teha Thonny kaudu või süsteemi käsurealt käsuga pip install numpy. Vajadusel loe läbi õpikus moodulite paigaldamise juhised.

Massiiv

Pythoni järjend ja ennik on üles ehitatud sellisele andmetüübile, mida kutsutakse massiiviks (ingl array). Massiiv on vanem andmetüüp, mis võib koosneda ainult ühte tüüpi väärtustest, mis paiknevad mälus järjest. Pythoni standardteegis on primitiivne massiiv realiseeritud moodulis array, aga see on üsna minimalistlik. Teek NumPy pakub sellise massiivi edasiarenduse, millel on võrreldes järjendiga järgmised omadused:

  • On mõeldud ühte tüüpi väärtuste hoidmiseks.
  • Elemendid paiknevad mälus järjest.
  • Elementide mälukasutus on väiksem.
  • Elementide lisamine ja eemaldamine on aeglasem, sest kogu massiiv tuleb mälus ümber kopeerida.
  • Elementide muutmine ja suurte andmehulkade töötlemine on üldiselt palju kiirem.

Järjend ja Numpy massiiv mälus. Allikas: Python Data Science Handbook

NumPy optimisatsioonid

NumPy massiive ei tasu töödelda niivõrd tsüklite abil, vaid tasub kasutada nende meetodeid, sobivaid funktsioone ja indekseerimist. NumPy käsud on kiiremad, sest nad kasutavad tsükleid, mis on kirjutatud C-keeles ja kompileeritud. Lisaks jaotavad käsud töö osadeks ja operatsioonid tehakse massiivi eri osade peal paralleelselt. Kasutatakse ära erinevaid protsessori omadusi ja optimisatsioone.

Selles peatükis mõeldaksegi edaspidi massiivi all just NumPy varianti.

Massiivi kuju ja teljed

Nagu järgmisel pildil on näha, võivad massiivid olla ka mitmemõõtmelise kujuga. Mälus püsivad elemendid alati ühes reas järjest, aga esitada võib neid erineval kujul. NumPyd kasutades on väga tähtis aru saada mõistetest kuju (ingl shape) ja telg (ingl axis).


Kahemõõtmelise NumPy massiivi esitus. Allikas: Stack Overflow

Kuju

Massiivi kuju määratakse loomishetkel, aga seda on võimalik hiljem jooksvalt muuta. Kahe rea ja kolme veeruga nullidest koosneva massiivi saab luua näiteks nii:

>>> import numpy as np
>>> kuju = (2,3)
>>> np.zeros(kuju)
array([[0., 0., 0.],
       [0., 0., 0.]])

Ühemõõtmeliste massiivide puhul on kuju sama mis elementide arv:

>>> kuju = 6
>>> np.zeros(kuju)
array([0., 0., 0., 0., 0., 0.])

0-mõõtmeline massiiv (punkt ehk skalaar) on põhimõtteliselt ka lubatud:

>>> np.array(np.pi)
array(3.14159265)

Ühe massiivi kuju saab kätte selle muutujaga shape:

>>> arr = np.zeros(3)
>>> arr.shape
(3,)

Tüüpilisemad vead, mis Numpy-ga töötades tekivad, on seotud sellega, et andmed on vale kujuga. Tihti annab NumPy veateate, aga mõnikord suudab ta ka vale kujuga midagi (ootamatut) teha. Veateate näide: massiivi kujuga 100, 2 ei saa täita kolmikutega:

>>> arr = np.full((100, 2), (3, 0.1, 2))
ValueError: could not broadcast input array from shape (3,) into shape (100,2)
Kuju muutmine

Kuna kuju muutmine ei muuda elementide paigutust mälus, siis on see operatsioon kiire. Massiivi saab ümber kujundada ainult siis, kui elemente on võimalik uuel kujul ümber paigutada:

>>> arr = np.zeros(9)
>>> arr = np.reshape(arr, (3,3))
>>> arr
array([[0., 0., 0.],
       [0., 0., 0.],
       [0., 0., 0.]])

>>> arr = np.reshape(arr, (3,2))
ValueError: cannot reshape array of size 9 into shape (3,2)

Teljed

Ühe massiivi tasemeid või mõõtmeid nimetatakse NumPys telgedeks (ingl axes). Need on nagu mitmemõõtmelise järjendi tasemed ning järjendiga, mille esimene tase (mõõde/telg 0) koosneb alamjärjenditest, saab ka luua vastava massiivi. Mõõde või telg 1 on aga read ise, mis antud näites sisaldavad arve:

>>> järjend = [ [1,0,1], [3,2,3], [4,5,4], [7,6,7] ]
>>> np.array(järjend)
array([[1, 0, 1],
       [3, 2, 3],
       [4, 5, 4],
       [7, 6, 7]])

>>> np.array(järjend).shape
(4, 3)

Sellise massiivi (või maatriksi) kuju on 4, 3: 4 alamosa, igaühes 3 elementi. Teisisõnu, esimese telje pikkus on 4, teise telje pikkus 3.

Telgedest võib ka mõelda kui ruumi telgedest (x, y, z, ...). Siis on ehk parem ette kujutada, et teljed on nummerdatud järjekorras alates kõrgeimast mõõtmest, nii et näiteks kolmemõõtmelise massiivi puhul:

  • Telg 0 on z-telg.
  • Telg 1 on y-telg.
  • Telg 2 on x-telg.

Suuremaid mõõtmeid võib olla raske intuitiivselt ette kujutada, aga õnneks ei lähe enamasti tarvis üle kahe mõõtme.

Indekseerimine

Massiivi indekseerimine toimib üldiselt samamoodi nagu teistegi Pythoni andmestruktuuride puhul, aga võimalusi on rohkem (ja võimsamaid!). Mitme mõõtme puhul saab kasutada näiteks komaga eraldatud indekseid või ennikuid.

>>> arr = np.array([ [1,3], [10,30], [100,300] ]) # Ülaltoodud joonisel keskel olev massiiv
>>> arr[0]
array([1, 3])
>>> arr[0, 0]
1
>>> arr[-1][0]
100
>>> arr[-1, 0]
100

Niimoodi saab valida ka terve veeru:

>>> arr[:,0]
array([  1,  10, 100])

Või miks mitte iga teise elemendi teises veerus:

>>> arr[::2,1]
array([  3, 300])
Elementide valimine järjendi või massiiviga

Kui kasutada indeksina järjendit või massiivi, toimib indekseerimine teistmoodi. Tagastatakse vastava telje elemendid etteantud järjekorras:

>>> arr[ [2, 0] ] # Read 2 ja 0
array([[100, 300],
       [  1,   3]])

>>> arr[1, [1, 0, 1, 0, 1]] # Teise rea elemendid kohtadel 1, 0, 1, 0, 1
array([30, 10, 30, 10, 30])
Tingimustega indekseerimine

Kui massiividega loogikatehteid teha, on tulemuseks tõeväärtuste massiiv. Tuleb välja, et tõeväärtustest koosnevaid massiive saab "filtritena" kasutada:

>>> arr[arr%2 == 0] # Valib kahega jaguvad elemendid
array([ 10,  30, 100, 300])

>>> arr[arr%2 == 0] = -1 # Asendab kõik kahega jaguvad elemendid
>>> arr
array([[ 1,  3],
       [-1, -1],
       [-1, -1]])

Mõned NumPy funktsioonid tagastavad indeksite või massiivide enniku, mida võib samamoodi indekseerimiseks kasutada. Näiteks funktsioon where annab nende massiivi elementide indeksid, kus tõeväärtus on tõene:

>>> indeksid = np.where(arr > 10)
>>> arr[indeksid]
array([ 30, 100, 300])
Indekseerimine ei tee koopiat!

Kui salvestada indeksite abil mingi lõik massiivist ja selle üksikuid elemente hiljem muuta, muutub ka algne massiiv:

>>> rida1 = arr[0,:]
>>> rida1[:] = np.array((-5, -10))
>>> rida1
array([ -5, -10])
>>> arr
array([[ -5, -10],
       [ 10,  30],
       [100, 300]])

Operatsioonid mööda ühte telge

Käskude puhul saab üldiselt määrata, millist telge pidi käsku täita tuleks. Et mööda-telge-operatsioonidest paremini aru saada, vaatame paari käsku. Teeme selle jaoks kõigepealt sellised massiivid, nagu olid viimasel joonisel:

arr1 = np.array(
      [[[  0,   1],
        [ 10,  11],
        [100, 101]],

       [[  0,   1],
        [ 10,  11],
        [100, 101]],

       [[  0,   1],
        [ 10,  11],
        [100, 101]]])

arr2 = np.array([ [1,3], [10,30], [100,300] ])
arr3 = np.array([4, 3])

np.sum

Väärtuste summeerimiseks on teegis olemas funktsioon sum, ilma telge täpsustamata tagastab ta kõikide elementide summa (kõik teljed/mõõtmed kaovad, koonduvad üheks arvuks):

>>> np.sum(arr1)
1017

Mis juhtub kui liita ainult mööda kõige sügavamat telge (x-telg)? Kokkuliitmine toimub ühte telge pidi ja see telg kaob:

>>> np.sum(arr1, axis=2)
array([[  1,  21, 201],
       [  1,  21, 201],
       [  1,  21, 201]])

Mööda telge 1 (y-telg):

>>> np.sum(arr1, axis=1)
array([[110, 113],
       [110, 113],
       [110, 113]])

Mööda telge 2 (ruumitelg z):

>>> np.sum(arr, axis=0)
array([[  0,   3],
       [ 30,  33],
       [300, 303]])

np.concatenate

Massiivide üksteise otsa liitmiseks on funktsioon concatenate. Sellele peab andma argumendiks massiivide loendi ja massiivid ühendatakse vaikimisi mööda telge 0. Etteantud massivid peavad olema ühesuguse kujuga, v.a. sellel teljel, mida mööda liidetakse.

>>> np.concatenate( (arr2, arr2) ) # Vaikimisi mööda telge 0
array([[  1,   3],
       [ 10,  30],
       [100, 300],
       [  1,   3],
       [ 10,  30],
       [100, 300]])
>>> np.concatenate( (arr2, arr2), axis=1 ) # Mööda telge 1
array([[  1,   3,   1,   3],
       [ 10,  30,  10,  30],
       [100, 300, 100, 300]])

Tüüpiline viga: Massiive arr2 ja arr3 ei saa kokku ühendada, sest neil pole esiteks telgede arv võrdne:

>>> np.concatenate( (arr2, arr3) )
ValueError: all the input arrays must have same number of dimensions, but the array at index 0 has 2 dimension(s) and the array at index 1 has 1 dimension(s)

Kui aga teha massiivile arr3 näiteks üks telg juurde, saab neid mööda telge 0 kokku liita küll:

>>> arr3 = np.array( [arr3] )
>>> arr3
array([[4, 3]]) 
>>> np.concatenate( (arr2, arr3) )
array([[  1,   3],
       [ 10,  30],
       [100, 300],
       [  4,   3]])

np.max ja np.argmax

Suurima väärtuse leidmiseks on funktsioon max ja vastava indeksi leidmiseks funktsioon argmax. Esimene on veidi lihtsam:

>>> np.max(arr2) # Suurim väärtus massiivis
300
>>> np.max(arr2, axis=0) # Suurimad väärtused mööda telge 0
array([100, 300])
>>> np.max(arr2, axis=1) # Suurimad väärtused mööda telge 1
array([  3,  30, 300])

argmax on veidi keerulisem. Näiteks ilma telge täpsustamata tagastab ta massiivi suurima väärtuse indeksi, eeldades, et massiiv om ühemõõtmeline. Et mitmemõõtmelises massiivis vastav väärtus leida, tuleb ka massiiv kõigepealt lamedale kujule viia või kasutada funktsiooni unravel_index:

>>> np.argmax(arr2)
5
>>> arr2.flat[5] # Vastav väärtus
300
>>> indeks = np.unravel_index(arr2.argmax(), arr2.shape)
>>> arr2[indeks]
300

Kui teljeparameeter ka anda, tagastab funktsioon indeksi, mis näitab, kus suurimad väärtused sellel teljel asuvad:

>>> np.argmax(arr2, axis=0)
array([2, 2], dtype=int64)

>>> np.argmax(arr2, axis=1)
array([1, 1, 1], dtype=int64)

Et sellele teljeindeksile vastavat väärtust kätte saada, tuleks indeksit veidi teisendada ning lõpuks kasutada funktsiooni take_along_axis:

>>> telg = 0
>>> indeks = np.argmax(arr2, axis=telg)
>>> indeks = np.expand_dims(indeks, telg)
>>> np.take_along_axis(arr2, indeks, telg)
array([[100, 300]])

Elementide andmetüüp

Vaikimisi on NumPy massiivides elemendid ujukomaarvudena või siis sama tüüpi, mis etteantud järjendis. Elementide tüübi saab ka täpsemalt määrata. Kasutada saab kõiki Pythoni lihttüüpe ja täisarvutüübid jaotuvad veel täpsemalt: Näiteks u1 hoiab ainult naturaalarve, mida saab esitada ühe baidi abil ehk arve 0-255. Nii saab mälu kokku hoida, kui on teada, et sellesse massiivi suuremaid ega negatiivseid väärtusi programmi töö ajal ei satu.

Ühte tüüpi saab tavaliselt mitmel moel tähistada ja tähistest saab kokku panna ka struktuurseid tüüpe. Kõik võimalikud tüübid leiad NumPy dokumentatsioonist: https://numpy.org/doc/stable/reference/arrays.dtypes.html. Siin on nimekiri tähtsamatest:

Andmetüübi nimiVõimalikud väärtused
u1täisarvud 0 - 255
u2täisarvud 0 - 65535
u8täisarvud 0 - 2**64-1
i1täisarvud -128 - 127
i8täisarvud -2**63 - 2**63-1
f ehk f4ujukomaarvud ligikaudu -3.4e+38 - 3.4e+38
d ehk f8ujukomaarvud ligikaudu -1.8e+308 - 1.8e+308
SASCII sümbolitega sõned (baitidena)
UUnicode sümbolitega sõned (töötab eesti tähtedega)
btõeväärtused
Osuvalised Pythoni objektid

NB! Kui kasutada kuskil vale andmetüüpi, ei pruugi alati veateadet näha, sest mõnel juhul suudab NumPy tüübi õigesti teisendada, teinekord aga võivad andmed hoopis muutuda:

>>> np.array([-1], "u4")
array([4294967295], dtype=uint32)

Massiivi elementide andmetüüp on mõistlik määrata loomise ajal, aga seda saab ka hiljem muuta meetodiga astype:

>>> arr = np.zeros(4)
>>> arr
array([0., 0., 0., 0.])

>>> arr = arr.astype("i")
>>> arr
array([0, 0, 0, 0], dtype=int32)

Ridadele võib isegi eraldi tüübi ja nime anda, nii et neid saab nime abil indekseerida. Näide ühest struktuursest tüübist, kus esimene rida (pealkirjaga "linn") koosneb sõnedest, teine rida ("pindala") koosneb ujukomaarvudest ja kolmas rida ("elanike arv") täisarvudest:

>>> tüüp = [("linn", "U15"), ("pindala", "f4"), ("elanike arv", int)]
>>> väärtused = [
       ("Tallinn", 159.3, 438341),
       ("Tartu", 38.8, 91407),
       ("Narva", 68.7, 53424),
       ("Pärnu", 33.2, 39605),
       ("Kohtla-Järve", 39.3, 32577),
       ("Rakvere", 10.64, 14984),
       ("Kuressaare", 15.5, 12933),
       ("Võru", 14, 11533),
       ("Haapsalu", 11.1, 9513)
]
>>> np.array(väärtused, dtype=tüüp)
array([('Tallinn', 159.3 , 438341), ('Tartu',  38.8 ,  91407),
       ('Narva',  68.7 ,  53424), ('Pärnu',  33.2 ,  39605),
       ('Kohtla-Järve',  39.3 ,  32577), ('Rakvere',  10.64,  14984),
       ('Kuressaare',  15.5 ,  12933), ('Võru',  14.  ,  11533),
       ('Haapsalu',  11.1 ,   9513)],
      dtype=[('linn', '<U15'), ('pindala', '<f4'), ('elanike arv', '<i4')])

Massiivi loomine

NumPy pakub mitmete operatsioonide jaoks palju erinevaid võimalusi ja käsuvariatsioone. Näiteks massiivi saab luua vähemalt 45 erineval viisil: sõnest, järjendist, failist, funktsioonist jne... Mõne käsuga saab kiiremini teatud kuju või sisuga massiivi luua:

FunktsioonKirjeldus
emptyLoob algväärtustamata massiivi.
zerosLoob nullidega täidetud massiivi.
onesLoob ühtedega täidetud massiivi.
fullLoob etteantud väärtusega täidetud massiivi.
full_likeLoob antud väärtusega täidetud ja antud massiivi kujuga uue massiivi.
eyeLoob 2D massiivi, mis on mööda diagonaale ühtedega täidetud, mujal nullid.
identityLoob ühikmaatriksi (mööda peadiagonaali ühtedega täidetud).
triLoob massiivi, kus diagonaal ja sellest ühele poole jääv ala on ühtedega täidetud.
arangeLoob 1D massiivi, toimib nagu Pythoni range.
linspaceLoob 1D massiivi, mis koosneb mingis vahemikus ühtlaselt jaotatud arvudest.
random.randomLoob massiivi, mis on täidetud juhuarvudega vahemikust [0,1).
random.standard_normalLoob massiivi, mis on valim juhuslikust normaaljaotusest.

Tehted massiividega

Massiividega tehete tegemise on NumPy väga mugavaks teinud:

>>> arr1 = np.arange(4)        # [ 0, 1, 2, 3]
>>> arr2 = np.arange(10, 10+4) # [10,11,12,13]
>>>
>>> arr1 + arr2
array([10, 12, 14, 16])
>>> arr1 - arr2
array([-10, -10, -10, -10])
>>> arr1 * arr2
array([ 0, 11, 24, 39])
>>> arr1 * 300
array([  0, 300, 600, 900])

Maatriksite ja vektorite korrutised


Maatriksteisendus. Allikas: xkcd.

Kasutusel on ka operaator @, mida Pythonis arvude vahel ei kasutata. See annab NumPys vektorite skalaarkorrutise või maatriksite korrutise:

>>> arr1 @ arr2 # Vektorite skalaarkorrutis
74
>>> arr1 = arr1.reshape((2,2)) # [ [0,   1], [2,   3] ]
>>> arr2 = arr2.reshape((2,2)) # [ [10, 11], [12, 13] ]
>>> arr1 @ arr2 # Maatriksite korrutis
array([[12, 13],
       [56, 61]])
>>> 

Vektorkorrutiseks tehtemärki eraldatud ei ole, kasutada tuleb funktsiooni cross.

Kõrgem matemaatika

NumPys on olemas vahendid ka veidi keerulisema algebraga tegelemiseks, näiteks determinantide arvutamiseks ja võrrandisüsteemide lahendamiseks. Need asuvad moodulites:

MoodulSisu
linalgLineaaralgebra
polynomialPolünoomidega arvutamine
fftFourier' teisendused

Funktsiooniga linalg.det saab ruutmaatriksite determinante leida. Võrrandisüsteemide lahendamiseks on aga mõistlik kasutada funktsiooni linalg.solve, millele tuleb parameetriks anda võrrandite liikmete kordajate maatriks ja vabaliikmete vektor. Näiteks järgmine võrrandisüsteem:

{$ \large\left\{\begin{array}{@{}l@{}} 2x_0 + 3x_1 = -2\\
-x_0 + \frac{1}{4}x_1 = 8 \end{array}\right. $}

Selle lahendid on {$ x_0=-7, x_1=4 $}:

>>> kordajad = [[2, 3], [-1, 1/4]]
>>> vabaliikmed = [-2, 8]
>>> np.linalg.solve(kordajad, vabaliikmed)
array([-7.,  4.])

Et polünoomidega arvutada, tuleb need kõigepealt luua:

>>> kordajad = [8, 0, -2] # -2x**2 + 8
>>> p = np.polynomial.Polynomial(kordajad)

Polünoomile 'p' vastab ruutvõrrand {$ -2x^2 + 8 = 0 $}. Meetodite abil saab nüüd leida polünoomi nullkohti, tuletisi ja integraale:

>>> p.roots() # Nullkohad (lahendid)
array([-2.,  2.])

>>> p.deriv(1) # Esimene tuletis
Polynomial([ 0., -4.], domain=[-1.,  1.], window=[-1.,  1.])

>>> p.deriv(1).integ(1) # Tuletise esimene määramata integraal
Polynomial([ 0.,  0., -2.], domain=[-1.,  1.], window=[-1.,  1.])

Loogilised tehted

Mõned loogilised tehted annavad tõeväärtuste massiivi. Võrrelda saab massiive nii arvude kui üksteisega:

>>> arr1 = np.zeros(5, dtype="u1")
>>> arr2 = np.ones(5, dtype="u1")
>>> arr1 < arr2
array([ True,  True,  True,  True,  True])
>>> arr1 == arr2
array([False, False, False, False, False])
>>> ~arr1 # not([0, 0, 0, 0, 0])
array([ True,  True,  True,  True,  True])

Täisarvude või tõeväärtuste massiividega saab teha ka bititehteid:

>>> arr1 = arr1.astype(bool)
>>> arr2 = np.array([True, False, True, False, True])

>>> arr1 & arr2 # AND
array([False, False, False, False, False])
>>> arr1 | arr2 # OR
array([ True, False,  True, False,  True])
>>> arr2 ^ True # XOR
array([False,  True, False,  True, False])
>>> arr2 ^ 1
array([0, 1, 0, 1, 0], dtype=int32)

Failist ja faili

Massiivi saab õigesti vormistatud tekstifailist ühe käsuga sisse lugeda:

 159;438341
 38;91407
 68;53424
 33;39605
>>> np.genfromtxt("fail.txt", dtype=int, delimiter=";")
array([[   159, 438341],
       [    38,  91407],
       [    68,  53424],
       [    33,  39605]])

Kui failis on reaalarvud, tuleks parameeter dtype vastavalt valida. Parameetritega missing_values ja filling_values on võimalik muuta seda, kuidas puuduvate väärtustega käitutakse.

Massiivi saab tekstifaili salvestada funktsiooniga savetxt. Käskudega save ja load on võimalik massiive salvestada ja sisse lugeda NumPy-spetsiifilises failivormingus:

>>> np.save("array.npy", arr)
>>> arr = np.load("array.npy")

Parameetreid saad täpsemalt uurida dokumentatsioonist vastavate funktsioonide alt: https://numpy.org/doc/stable/reference/routines.io.html.

Kui on tarvis lugeda andmeid näiteks tabelkujul failidest, siis on mõistlikum kasutada teeki pandas, mis on just selle jaoks mõeldud ja toimib NumPyle väga sarnaselt.

Käskude kokkuvõte ja spikker

Kui massiivi loomiseks oli juba tohutult võimalusi, siis võib eeldada, et funktsioonide ja meetodite arv NumPys on päris suur. Siin on veel mõned, mida tasub ära mainida:

Elemendikaupa töötavad funktsioonid
absArvutab massiivi (iga elemendi) absoluutväärtuse.
addLiidab massiivid elemendikaupa nagu vastava tehtega, aga argumentidega saab käitumist rohkem juhtida.
add.accumulateLiidab massiivid elemendikaupa kumulatiivselt.
apply_along_axisRakendab etteantud funktsiooni mööda telge.
array_equalTagastab True, kui massiivide kuju ja elemendid on võrdsed, muidu False.
gcdLeiab sama kujuga massiivide vastavate elementide suurimad ühisnimetajad.
corrcoefTagastab kuni kahemõõtmelis(t)e massiivi(de) Pearsoni korrelatsioonikordajate maatriksi.
gradientTagastab massiivi gradiendi.
iscloseVõtab parameetriks kaks massiivi ja tagastab sama kujuga tõeväärtuste massiivi, kus iga element ütleb, kas antud massiivide elemendid sellel kohal on võrdsed mingi hälbe piires.
sinArvutab massiivi (iga elemendi) siinuse.
Massiivi kuju või suurust töötlevad funktsioonid
array_splitTükeldab massiivi.
concatenateÜhendab massiivid.
deleteKustutab massiivist elemente, tagastab uue massiivi.
expand_dimsLisab massiivi uue telje, tagastab paisunud kujuga massiivi.
flipTagastab massivi peegeldatud kuju.
insertSisestab massiivi väärtused, tagastab uue massiivi.
packbitsPakib kahendarvude massiivi bittidena i1 tüüpi massiiviks.
padTäidab massiivi mingeid külgi pidi mingi(te) väärtustega. Nt. loob pildile raami.
repeatDubleerib massiivi elemente. Tagastab paisunud massiivi.
resizeTagastab uue kuju ja suurusega massiivi.
rollTagastab ühte telge pidi nihutatud massiivi. Viimased väärtused lähevad esimeseks.
rot90Tagastab 90 kraadi pööratud massiivi.
swapaxesVahetab massiivi kaks telge omavahel, tagastab uue massiivi.
tileDubleerib massiivi mingi arv kordi mingite telgede suunas.
Otsingufunktsioonid
searchsortedAnnab sorteeritud massiivi puhul indeksid, kuhu antud elemendid sisestada tuleks, et järjestatus säiliks.
uniqueTagastab kõik massiivis esinevad erinevad väärtused kasvavas järjekorras.
whereTagastab tingimuse (filtri) põhjal indeksid, kus tingimus kehtib. Kui anda lisaargumentideks 2 massiivi, valib tõese indeksi puhul väärtused ühest massiivist, muidu teisest.
Hulgatehted massiividega (vt. ka funktsiooni unique)
isinVõtab parameetriks kaks massiivi ja tagastab esimese massiivi kujuga tõeväärtuste massiivi, kus iga element ütleb, kas esimese massiivi vastav element leidus teises massiivis.
union1dTagastab massiivide ühendi.
intersect1dTagastab massiivide ühisosa.
setdiff1dTagastab elemendid esimesest massiivist, mida teises pole (vahe).
setxor1dTagastab elemendid, mida mõlemas massiivis pole (sümmeetriline vahe).

Paljud funktsioonid on saadaval ka massiivimeetoditena, aga kui kasutada mõlemaid, siis tasub tähele panna, et funktsioonid tagastavad üldjuhul massiivi muudetud koopia, aga mõned meetodid muudavad olemasolevat massiivi (tabelis ära märgitud). Näiteks massiiv.sort sorteerib massiivi, aga np.sort võtab parameetriks massiivi ja tagastab selle sorteeritud koopia. Teatud käskudel on parameeter inplace, mis seda käitumist muudab. Näited erinevatest meetoditest:

MeetodKirjeldus
astypeMuudab massiivi elementide tüübi (tagastab koopia).
clipAsendab kõik ülem-/alampiirist suuremad/väiksemad elemendid piirväärtusega.
fillAsendab massiivis kõik väärtused ühe väärtusega (ei tagasta, muudab).
flattenTagastab massiivi ühemõõtmelisel kujul.
maxTagastab massiivi suurima elemendi.
minTagastab massiivi väikseima elemendi.
meanTagastab massiivi elementide keskmise.
nonzeroTagastab indeksid, kus olev väärtus pole 0.
ptpPeak-to-peak: Tagastab massiivi suurima ja vähima elemendi vahe.
repeatDubleerib massiivi elemente.
resizeMuudab massiivi suurust ja kuju (ei tagasta, muudab; parem on kasutada vastavat funktsiooni).
reshapeTagastab muudetud kujuga massiivi.
roundÜmardab massiivi elemendid.
sortSorteerib massiivi (muudab massiivi, vaikimisi mööda viimast telge).
squeezeEemaldab massiivist teljed, mille pikkus on 1.
sumTagastab elementide summa.
traceTagastab diagonaali(de) elementide summa.
transposeTagastab transponeeritud massiivi.
tofileKirjutab massiivi faili.
tolistTeisendab massiivi järjendiks.

Igal massiivil on järgmised muutujad:

MuutujaKirjeldus
shapeMassiivi kuju.
sizeMassiivi elementide arv. len(massiiv) annab ainult 0-telje pikkuse.
itemsizeÜhe elemendi pikkus baitides.
dtypeElementide tüüp.
ndimMassiivi mõõtmete või telgede arv.
TMassiiv transponeeritud kujul.

Siin juhendis me NumPy mooduleid lähemalt ei uuri, aga hea on teada, milliseid mooduleid NumPys veel leidub:

Teegiga töötades on hea dokumentatsiooni või spikrit kõrval hoida. Dokumentatsiooni algus on siin: https://numpy.org/doc/stable/reference/index.html

Siinset silmaringimaterjali võib kasutada spikrina. Rohkem spikreid tasub otsida märksõnaga NumPy cheatsheet. Järgnevalt lingilt leiab ühe variandi: https://www.datacamp.com/cheat-sheet/numpy-cheat-sheet-data-analysis-in-python.

Andmeteadus ja masinõpe

NumPyd täiendavad või kasutavad alusena ka mitmed teised teegid, eriti need, mis on seotud andmeteadusega. NumPy tundmine teeb nendega töötamise ka oluliselt kergemaks. Tihti nende teekide funktsioonid tagastavad või võtavad parameetriks ka NumPy massiive.

  • Matplotlib on teek, mis on mõeldud andmete visualiseerimiseks, jooniste tegemiseks ja kuvamiseks.
  • Seaborn sisaldab rohkem huvitavamaid kujutamisvõimalusi.
  • Pandas on mõeldud tabelandmete sisselugemiseks, töötlemiseks ja analüüsimiseks.
  • Scipy sisaldab palju teaduslikke funktsioone: keerulisemad matemaatilised tehted, andmete klasterdamine, helisignaali ja pilditöötluse funktsioonid, integreerimine ja võrrandite lahendamine.
  • Sklearn pakub mugavalt kasutatavaid masinõppe algoritme.
  • Keras pakub rohkem sügavõppe algoritme.
  • PyTorch on veel üks sügavõppe teek. Kiirem, aga keerulisem kasutada kui Keras.

Põhjalikumalt saab nende teekidega tutvuda andmeteadust või tehisintellekti käsitlevatel kursustel, näiteks:

  • LTAT.01.003 Tehisintellekt
  • LTAT.02.017 Tehisintellekti algkursus
  • LTAT.02.002 Sissejuhatus andmeteadusesse

Andmeteadus Pythoniga. Allikas.

Enesekontrolliküsimused

Ülesanded

1. Koosta programm, mis küsib kasutajalt sisendiks kaks maatriksit või vektorit ning kuvab vastusena nende

  • skalaarkorrutise
  • vektorkorrutised
  • vastavate elementide lihtsamate aritmeetiliste tehete tulemused: summa, vahe, korrutis, jagatis
  • ühisosa elemendid

Kui mõnda tehet või operatsiooni ei saa mingil põhjusel teha, tuleb kasutajale põhjus väljastada!

2. Järgmiselt veebilehelt leiab 101 NumPy teisendusharjutust, proovi mõningaid lahendada: https://www.machinelearningplus.com/python/101-numpy-exercises-python/.

3. Kirjuta programm, mis küsib kasutajalt tabelifaili (nt. Exceli või CSV-failid) nime ja loeb faili sobivasse NumPy massiivi. Seejärel võiks programm väljastada parameetreid ja infot andmete kohta. Näiteks:

  • Ridade/veergude keskmised väärtused
  • Enimesinevad väärtused
  • Suurimad, vähimad väärtused
  • Ridade/veergude väärtuste korrelatsioonid, seosed
  • Väärtuste osakaalud

Vali lisaks NumPyle veel vähemalt üks andmeteaduse teek, mida selles ülesandes ära kasutada saaksid. Ideed:

  • Kujuta andmeid ja nende seoseid. Uuri huvitavaid kujutamisvõimalusi: Top 50 matplotlib Visualizations.
  • Kui sul on palju andmeid (100 000+ rida), proovi üks väärtusi ennustav masinõppe mudel treenida.

4. Vaata, kas oled kirjutanud mõne programmi, mis töötleb järjendite abil suurt hulka andmeid, näiteks pilte või heli. Asenda järjendid nüüd sobivates kohtades NumPy massiividega ja proovi, kas see teeb programmi efektiivsemaks.

  • Institute of Computer Science
  • Faculty of Science and Technology
  • University of Tartu
In case of technical problems or questions write to:

Contact the course organizers with the organizational and course content questions.
The proprietary copyrights of educational materials belong to the University of Tartu. The use of educational materials is permitted for the purposes and under the conditions provided for in the copyright law for the free use of a work. When using educational materials, the user is obligated to give credit to the author of the educational materials.
The use of educational materials for other purposes is allowed only with the prior written consent of the University of Tartu.
Terms of use for the Courses environment