1.2 Failide tüübid ja nende sisu¶
1.2.1 Tekstifail vs. binaarne fail¶
Kõik arvutis salvestatud failid sisaldavad andmeid binaarsel kujul $-$ on binaarsed failid. Fundametaalsel tasemel eristatakse kõigest kahte tüüpi failile. Pythonis ja mujal eristame binaarseid- ja tekstifaile. Kusjuures tekstifail on binaarne fail mille sisu tõlgendatake kui teksti. Kõiki faile on võimalik jagade kas binaarseks või tekstifailiks. Lisainfo: https://fileinfo.com/help/binary_vs_text_files
Andmete esitus failis:
Binaarsed failid
- Andmed kirjutatakse faili nii nagu need on esitatud arvuti mälus.
- Andmed loetakse failist mällu otsese kopeerimisega, programmid võivad andmeid interpreteerida.
Tekstifailid
- Eeldatakse, et binaarsed andmed on tekstimärkide koodid.
- Andmete lugemisel tekstiredaktorid interpreteerivad andmeid tekstina (dekodeerimine ja kodeerimine).
1.2.2 Sõne esitus arvuti mälus¶
Sõne on muutmatu (immutable) objekt, mis esindab tähemärkide jada. Igal märgil on täisarvuline kood ja graafiline esitus (šrift, inglise k. font). Arvuti mälus on sõned esitatud eelmainitud koodide jadana. Kuvaril näidatakse sõnet kasutades selle tähemärkide graafilist esitust. Klaviatuuri nupule vajutus genereerib vastava märgi koodi. Pythoni sõned kasutavad vaikimisi nn. Unicode tähemärke (kodeeringuga UTF-8). Loe lisaks: https://docs.python.org/3/howto/unicode.html
Näiteks tähemärgile a vastav kood on 97. Koodile 107 vastav tähemärk on k, jne.:
ord('a') # Funktsioon ord ehk ordinaal.
97
Ordinaalile 97 vastav tähemärk on:
chr(97)
'a'
Igat täisarvu saame esitada binaarsel kujul:
bin(97)
'0b1100001'
Tähemärgi ordinaal on tavaliselt 8 bitine:
'0' + bin(97)[2:] # Tavaliselt 8 bitine.
'01100001'
Kodeering UTF-8 toetab kõiki suuremaid tähemärkide rühmi. Näiteks:
chr(231)
'ç'
1.2.2.1 Sõne "Juulius"¶
Sõne "Juulius" esitus arvuti mälus:
fraas = 'Juulius'
binary = ''
for mark in fraas:
o = ord(mark) # 'a' --> 97
b = bin(o) # 97 --> '0b1100001'
b = b[2:] # '0b1100001' --> '1100001'
b = b.zfill(8) # '1100001' --> '01100001'
binary += b # Konkatenatsioon.
print(binary) # --> 01001010 01110101 01110101 01101100...
01001010011101010111010101101100011010010111010101110011
1.2.2.2 Pildifail Juulius.png ja tekstiredaktor¶
Binaarseid faile ehk mitte-tekstifaile on võimalik avada ka tekstiredaktoris (vt. Jooniseid 1 ja 2), kuid nende sisu ei ole inimesele loetaval kujul. Joonistel 1 (paremal) ja 2 (paremal) toodud näidetes tõlgendab tekstiredaktor pildifailides sisalduvad binaarandmed – nullide ja ühtede jadad – tähemärkide koodidena, mistõttu kuvatav teave ilmub juhusliku ja arusaamatu tekstina.
| Joonis 1. (Vasak) Binaarne pildifail avatuna pildikuvamise tarkvaraga. (Parem) Binaarne pildifail vasakpoolselt jooniselt avatuna lihtsas tekstiredaktoris. |
Joonis 2 kasutab .jpg formaadis fotofaili.
| Joonis 2. (Vasak) Binaarne pildifail avatuna pildikuvamise tarkvaraga. (Parem) Binaarne pildifail vasakpoolselt jooniselt avatuna lihtsas tekstiredaktoris. |
2 Failihaldus Pythonis¶
2.1 Sisseehitatud funktsioon open ja failiobjekt¶
Failide avamiseks kasutame sisseehitatud funktsiooni open. Faile saab avada erinevates režiimides (nimega vaikeväärtusega argument mode). Kui pole teisiti otsustatud siis Python eeldab, et andmed on tõlgenadatavad sõne andmetüübina nii andmete lugemisel kui ka kirjutamisel.
Pythoni faili esindab failiobjekt mis on iteraator. Üle failiobjekti saab itereerida. Itereerimisel itereeritakse kas rida rea või bait baidi haaval. Tekstifailis vastab ühele baidile üks tähemärg. 1 bait (B) = 8 bitti.
Loeme sisseehitatud funktsiooni open dokumentatsiooni:
#help(open) # Loe iseseisvalt.
2.1.1 Töökaustas oleva faili loomise ja lugemine süntaks¶
Faili avamine kasutades sisseehitatud funktsiooni open mis tagastab failiobjekti:
<muutuja> = open("<faili nimi>.<laiend>", "r") # Režiim 'r' ehk read mode (vaikeväärtus).
Uue faili loomine:
<muutuja> = open('<faili nimi>.<laiend>', 'w') # Režiim 'w' ehk write mode.
Peale faili avamist ja sellega töötamist tuleb see alati sulgeda. Kasutame failiobjekti meetodit close:
<muutuja>.close()
Faili sõne kirjutamiseks kasutame meetodit write :
<muutuja>.write(<andmed>)
Märkus: NB! Kui fail eksisteerib ja selles on andmeid siis vaikimisi kirjutab meetod write olemasolevad andmed üle.
Failist lugemiseks (kogu sisu korraga, kõik baidid korraga) kasutame meetodit read. Meetod read itereerib üle failiobjekti mis on iteraator. Faili sisse lugemine ammendab iteraatori:
<muutuja>.read()
2.1.2 Faili asukohale viitamine¶
Kui avad Pythonis faili, pead sellele ette andma failitee (path) – see on aadress, mis näitab Pythonile, kus fail sinu arvutis asub.
Aadresse on kahte põhitüüpi:
- Absoluutne aadress
- Suhteline aadress
2.1.2.1 Absoluutne aadress¶
Näitab faili täpset asukohta alates failisüsteemi juurkataloogist. Töötab sõltumatult sellest, kus sinu Pythoni moodul asub.
Näide (Windows):
f = open("C:\\Users\\Juulius\\Documents\\data.txt") # Meeldetuletus \ on sõne escape tag.
või
f = open(r"C:\Users\Juulius\Documents\data.txt") # Kasuta r, et luua raw-string.
või (soovituslikult)
f = open("C:/Users/Juulius/Documents/data.txt") # Muudab taustal kujule \\.
Näide (macOS ja Linux):
f = open("/home/Juulius/Documents/data.txt")
2.1.2.2 Suhteline aadress¶
Näitab faili asukohta praeguse töökausta (mooduli asukoha) suhtes.
Näited (kõik platvormid toetatud, Windowsi puhul teisendab taustal kujule \):
f20 = open("../../other/data.txt") # Kaks kausta ülespoole.
f10 = open("../other/data.txt") # Üks kaust ülespoole.
f00 = open("data.txt") # Fail samas kaustas kus moodul.
f01 = open("other/data.txt") # Fail alamkaustas.
f02 = open("info/other/data.txt") # Fail alam-alamkaustas.
2.1.3 Faili kirjutamise ja lugemise näide¶
Loome faili (vaikimisi luuakse see töökausta) ja kirjutame sellesse sõne 'Juulius Tipikas on maskott.':
f = open('Juulius.txt', 'w') # Loob faili töökausta.
f.write('Juulius Tipikas on maskott.')
f.close() # Ära unusta fail sulgeda.
Avame loodud faili ja loeme selle sisu:
f = open('Juulius.txt') # Vaikimisi režiim 'r'.
print(dir(f)) # Objekti meetodid ja atribuudid.
print()
print(type(f)) # Failiobjekt on iteraator.
print(iter(f)) # Failiobjekt on iseenda iteraator.
print(f.name) # Atribuut.
print('mode =', f.mode) # Atribuut.
print()
print(f.read()) # Loeme sisu ja prindime konsooli.
f.close() # Ära unusta fail sulgeda.
['_CHUNK_SIZE', '__class__', '__del__', '__delattr__', '__dict__', '__dir__', '__doc__', '__enter__', '__eq__', '__exit__', '__format__', '__ge__', '__getattribute__', '__getstate__', '__gt__', '__hash__', '__init__', '__init_subclass__', '__iter__', '__le__', '__lt__', '__module__', '__ne__', '__new__', '__next__', '__reduce__', '__reduce_ex__', '__repr__', '__setattr__', '__sizeof__', '__str__', '__subclasshook__', '_checkClosed', '_checkReadable', '_checkSeekable', '_checkWritable', '_finalizing', 'buffer', 'close', 'closed', 'detach', 'encoding', 'errors', 'fileno', 'flush', 'isatty', 'line_buffering', 'mode', 'name', 'newlines', 'read', 'readable', 'readline', 'readlines', 'reconfigure', 'seek', 'seekable', 'tell', 'truncate', 'writable', 'write', 'write_through', 'writelines'] <class '_io.TextIOWrapper'> <_io.TextIOWrapper name='Juulius.txt' mode='r' encoding='UTF-8'> Juulius.txt mode = r Juulius Tipikas on maskott.
2.2 Kontekstihaldur, konstruktsioon with/open/as¶
Selleks, et mitte muretseda ega unustada failide sulgemist on loodud kontekstihaldur ehk with-plokk.
2.2.1 Kasutus ja süntaks¶
Konstruktsiooni with/open/as kasutamise süntaks:
with open('<faili nimi>.<laiend>', 'w') as <nimi>:
<nimi>.write('Faili sisu')
with open('<faili nimi>.<laiend>', 'r') as <nimi>:
sisu = <nimi>.read()
Märkus: with-plokist väljaspool on fail automaatselt suletud.
2.2.2 Näide¶
Loome faili ja lisame sellesse sõne 'Juulius Tipikas on maskott.\nTema õde on Juulia.'. Mis tähendab, et faili sisu saab olema kujul:
Juulius Tipikas on maskott.
Tema õde on Juulia.
Faili suletuse staatust saab järgi vaadata objekti muutuja closed abil:
with open('Juulius.txt', 'w') as f: # Proovi ka muid faili laiend näiteks .dat, .csv jne.
f.write('Juulius Tipikas on maskott.\nTema õde on Juulia.')
print(f.closed) # Suletud või mitte?
f.closed # Suletud või mitte?
False
True
Avame faili ja loeme selle sisu:
with open('Juulius.txt', 'r') as f:
sisu = f.read() # Kogu sisu korraga itereerides üle faili (kõik baidid korraga).
print(sisu)
Juulius Tipikas on maskott. Tema õde on Juulia.
2.3 Failiobjekti meetodid: writelines, readlines, readline, seek, tell¶
Lisaks eelmainitud meetoditele write ja read on failiobjektil ka teisi meetodeid. Allpool näitame valitud meetodite kasutamise näiteid.
2.3.1 Meetod writelines¶
Märkus: Meedodit writeline pole olemas (vt. allpool, vrd. meetodiga readline).
Meetod kirjutab faili mitu sõnet korraga. Paiguta sõned iteraatortoega objekti, nt listi:
with open('Juulius.txt', 'w') as f: # Proovi ka muid faili laiend näiteks .dat jne.
data = ['Juulius\n', 'Juulia']
f.writelines(data)
with open('Juulius.txt', 'r') as f:
sisu = f.read() # Kogu sisu korraga (kõik baidid korraga).
print(sisu)
Juulius Juulia
rows = ('Juulius Tipikas on maskott.\n', 'Tema õde on Juulia.') # NB! reavahetus.
with open('Juulius.txt', 'w') as f: # Proovi ka muid faili laiend näiteks .dat jne.
f.writelines(rows)
with open('Juulius.txt', 'r') as f:
sisu = f.read() # Kogu sisu korraga (kõik baidid korraga).
print(sisu)
Juulius Tipikas on maskott. Tema õde on Juulia.
2.3.2 Meetod readlines¶
Meetod loob loetud ridu sisaldava loendi itereerides üle failiobjekti (ammendab iteraatori):
with open('Juulius.txt', 'r') as f:
sisu = f.readlines() # Kõik teksti read listi sisu.
print(sisu)
print()
for rida in sisu: # Itereerin üle listis olevate ridade.
print(rida, end='') # Argument end, et ei tekiks tühja lisarida.
['Juulius Tipikas on maskott.\n', 'Tema õde on Juulia.'] Juulius Tipikas on maskott. Tema õde on Juulia.
Kuna loetud read on paigutatud listi saame kasutada listiga kaasasolevaid võimalusi:
with open('Juulius.txt', 'r') as f:
sisu = f.readlines()[1:] # Indekseerimine: Alates indeks = 1.
print(sisu)
print()
for rida in sisu: # Itereerin üle listi sisu.
print(rida)
['Tema õde on Juulia.'] Tema õde on Juulia.
2.3.3 Meetod readline¶
Meetod teostab ühe realugemise ehk loeb kuni reavahetuseni. Meetod on iteratiivne:
with open('Juulius.txt', 'r') as f:
sisu = f.readline() # Fail f on iteraator, readline on analoogne iteraatori __next__ meetodiga.
print(sisu, end='')
sisu = f.readline() # Mäletab viimati loetud rida. Järgmine iteraat.
print(sisu)
Juulius Tipikas on maskott. Tema õde on Juulia.
with open('Juulius.txt', 'r') as f:
for _ in range(2):
rida = f.readline() # Fail f on iteraator, readline on analoogne iteraatori __next__ meetodiga.
print(rida, end='')
Juulius Tipikas on maskott. Tema õde on Juulia.
Nagu eelpool mainitud on failiobjekt iteraator. Seda kinnitas ka eelmine näide. Kas me saame üle faili itereerida? Üle failiobjekti saab lugemise režiimis 'r' itereerida:
with open('Juulius.txt', 'r') as f:
for rida in f: # Itereerime üle failiobjekti.
print(rida, end='') # Eemaldame esimese rea lõpus oleva reavahetuse.
Juulius Tipikas on maskott. Tema õde on Juulia.
Lisaks eelmainitule võtab meetod read vastu argumendi mis tähistab baitide arvu milleni failisisu itereerida ehk lugeda (mitu baiti lugeda):
with open('Juulius.txt', 'r') as f:
sisu = f.read(7) # Mitu baiti loeme: 1 B = 1 tähemärk.
print(sisu)
sisu = f.read(8) # Järgmised 8 baiti, mäletab viimati loetud baiti.
print(sisu)
Juulius Tipikas
2.3.4 Meetod tell¶
Meetod tagastab lugemise asukoha avatud ja hetkel loetavas failis esitatuna baitides:
with open('Juulius.txt', 'r') as f:
sisu = f.read(7) # Mitmenda baidini loeb.
print(sisu)
print('Kus asun:', f.tell()) # Mitmes bait hetkel.
sisu = f.read(20) # Leme järgmised 20 B.
print(sisu)
print('Kus asun:', f.tell())
Juulius Kus asun: 7 Tipikas on maskott. Kus asun: 27
2.3.5 Meetod seek¶
Meetod lubab baitides esitatud asukohta muuta või määrata:
with open('Juulius.txt', 'r') as f:
sisu = f.read(7) # Loeb 7 baiti.
print(sisu)
f.seek(0) # Liigume faili algusesse.
sisu = f.read(15) # Loen algusest 15 baiti.
print(sisu)
print('Kus asun:', f.tell())
Juulius Juulius Tipikas Kus asun: 15
Näide: Kirjutan with-plokis eelnevalt faili kirjutataud teksti üle:
with open('Juulius.txt', 'w') as f:
f.write('Juulius Tipikas on maskott.') # Algne tekst, loodud sisu.
f.seek(19) # Liigub baitidevoos siia.
f.write('eeskujulik kodanik\n') # Kirjutan üle alates bait 19.
for i in range(2):
f.write('Eeskujulik kodanik!\n') # Lisan veel teksti.
with open('Juulius.txt', 'r') as f:
sisu = f.read()
print(sisu)
Juulius Tipikas on eeskujulik kodanik Eeskujulik kodanik! Eeskujulik kodanik!
3 Failidega töötamine¶
Siin lõigus tutvustame muid tegevusi failidega.
3.1 Faili kopeerimine¶
Faile saab kopeerida kasutades pesastatud with-plokke. Tekstifaili kopeerimine:
with open('Juulius.txt', 'r') as rf:
with open('Juulius_copy.txt', 'w') as wf:
for line in rf:
wf.write(line)
Binaarse pildifaili kopeerimine:
with open('Juulius.png', 'rb') as rf:
sisu = rf.read()
with open('Juulius_copy.png', 'wb') as wf:
wf.write(sisu)
with open('Juulius.png', 'rb') as rf:
with open('Juulius_copy.png', 'wb') as wf:
for line in rf:
wf.write(line)
Kui kopeeritav fail on arvuti operatiivmälu jaoks liiga suur. Kopeerime seda osade kaupa:
with open('Juulius.png', 'rb') as rf:
with open('Juulius_copy.png', 'wb') as wf:
jupp = rf.read(30) # 30-ne B kaupa.
while len(jupp) > 0:
wf.write(jupp)
jupp = rf.read(30)
3.2 Lausend with ja mitme faili avamine korraga¶
Lausend with toetab mitme faili samaaegset avamist. Faili kopeerimiese näide:
with open('Juulius.png', 'rb') as rf, open('Juulius_copy.png', 'wb') as wf:
for line in rf:
wf.write(line)
3.3 Failis olevatele andmetele uute andmete lisamine¶
Kas faili saab lisada andmeid meetodiga write nii, et see ei kirjutaks üle olemasolevaid andmeid (ei looks uut failisisu). Selleks saame kasutada meetodeid write ja writelines koos faili kasutamise režiimiga 'a' (append):
with open('Juulius.txt', 'a') as f:
for _rida in range(2):
f.write(' Lisame uue rea.\n') # NB! Ära unusta reavahetust rea lõpus.
with open('Juulius.txt', 'a') as f:
for _rida in range(2):
f.write(' LISAME UUE REA.\n') # NB! Ära unusta reavahetust rea lõpus.
with open('Juulius.txt', 'r') as f:
sisu = f.read()
print(sisu)
Juulius Tipikas on eeskujulik kodanik Eeskujulik kodanik! Eeskujulik kodanik! Lisame uue rea. Lisame uue rea. LISAME UUE REA. LISAME UUE REA.
Sarnaselt töötab ka faili meetod writelines:
lines = ['Python ', 'on ', 'madu.']
with open('Juulius.txt', 'a') as f:
f.writelines(lines)
with open('Juulius.txt', 'r') as f:
sisu = f.read()
print(sisu)
Juulius Tipikas on eeskujulik kodanik Eeskujulik kodanik! Eeskujulik kodanik! Lisame uue rea. Lisame uue rea. LISAME UUE REA. LISAME UUE REA. Python on madu.
4 Andmete serialiseerimine¶
Serialiseerimine on tegevus kus andmed teisendatakse baitide jadaks ja salvestatakse kuskile.
4.1 Standardteegi moodul pickle¶
Moodul pickle serialiseerib Pythoni objektid baitide jadaks (nullideks ja ühtedeks) ja tagasi. Joonis 3 kujutab serialiseerimise protsessi visuaalselt.
- Igat Pythoni objekti saab serialiseerida ja salvestada kettale.
- Loodud baitide jada sisaldab kogu informatsiooni mis on vajalik teisel Pythoni moodulil objekti taastamiseks.
Joonis 3. Meem moodulile pickle. |
Kasutamise näide, objekti sealiseerimiseks kasutame meetodit dump ja desearialireerimiseks meetodit load:
import pickle
data = dict(a = 1, b = [1, 2])
f = open('Juulius.pkl', 'wb') # Kasuta .pkl faililaiendit.
pickle.dump(data, f)
f.close()
f = open('Juulius.pkl', 'rb')
print(pickle.load(f)) # --> {'a':1, 'b':[1, 2]}
f.close()
{'a': 1, 'b': [1, 2]}
Kasutus koos kontekstihalduriga ehk with-plokis:
import pickle
data = dict(a = 1, b = [1, 2, 3])
with open('Juulius.pkl', 'wb') as f:
pickle.dump(data, f)
with open('Juulius.pkl', 'rb') as f:
print(pickle.load(f))
{'a': 1, 'b': [1, 2, 3]}
4.2 Standardteegi moodul shelve¶
Moodul shelve on salvestuv sõnaraamat, kus andmeid salvestatakse baitide jadadena.
- Moodulit kasutatakse siis kui keerulisemate andmebaaside kasutus pole õigustatud.
- Andmete lugemiseks kasutame võtmenimesid nii nagu sõnastikes.
- Salvestamisel andmed serialiseeritakse.
Joonis 4 kujutab meemi mis piltlikustab mooduli shelve poolt loodud serialireeritud andmeid. Jooniste 3 ja 4 võrdlus piltlikustab moodulite pickle ja shelve salvestatud andmete struktuuride erinevust.
Joonis 4. Meem moodulile shelve. |
Mooduli shelve kasutamise näide:
import shelve
f = shelve.open('Juulius') # Faililaiendit .db pole vaja lisada.
f['a'] = 1 # Lisan võtmesõna ja väärtuse paari.
f['b'] = [1, 2, 3, 'd'] # Lisan võtmesõna ja väärtusi paari.
f.close()
f = shelve.open('Juulius')
print(f['a']) # --> 1
print(f['b']) # --> [1, 2, 3, 'd']
f.close()
1 [1, 2, 3, 'd']
Kasutus koos kontekstihalduriga ehk with-plokis:
import shelve
with shelve.open('Juulius') as f: # laiendit .db pole vaja kasutada
f['a'] = 1
f['b'] = [1, 2, 3, 'd']
f['c'] = 'Juuliuse kallistamine ei ole kuritegu.'
with shelve.open('Juulius') as f:
print(f['a'])
print(f['b'])
print(f['c'])
1 [1, 2, 3, 'd'] Juuliuse kallistamine ei ole kuritegu.
5 CSV failide kasutamine¶
Comma Separated Values (CSV) on üks lihtsamaid, vanimaid ja universaalsemaid tekstifaili failivorminguid, kus andmed on üksteisest eraldatud semikoolonitega, komadega, taandetega või muude sümbolitega. Andmed kirjutatakse ridadesse ja veergudesse. Andmete lugemisega saavad hakkama nii tavalised kontoritööprogrammid (MS Word, OpenOffice, LibreOffice), kui ka lihtsad tekstiredektorid nagu Notepad jne.
CSV faili sisu võib olla järgmine:
No, Name, Contribution
1, Linus Torvalds, Linux Kernel
2, Tim Berners-Lee, World Wide Web
3, Guido van Rossum, Python Programming
4, Juulius Tipikas, None
Loodusteadlased salvestavad tihti numbrilisi väärtusi CSV faili:
no.; time (s); speed (m/s)
0; 0.00; 12.4376
1; 1.00; 12.6432
2; 2.00; 13.6676
3; 3.00; 14.7628
4; 4.00; 13.4772
5.1 Standardteegi moodul csv¶
CSV tüüpi tekstifailide importimiseks ja loomiseks on loodud moodul mis on Pythoni standardteegi osa. Lisainfo: https://docs.python.org/3/library/csv.html
5.1.1 Tavakasutuse näiteid, funktsioon csv.writer ja failiobjekti meetod writerow¶
Loome faililaiendiga .csv tekstifaili, selle sisu ja loeme selda. Funktsioon csv.writer tagastab failiobjekti:
import csv
with open('Juulius.csv', 'w') as f:
k = csv.writer(f, delimiter=',')
k.writerow(['No', ' Name', ' Contribution'])
k.writerow(['1', ' Linus Torvalds', ' Linux Kernel'])
k.writerow(['2', ' Tim Berners-Lee', ' World Wide Web'])
k.writerow(['3', ' Guido van Rossum', ' Python Programming'])
k.writerow(['4', ' Juulius Tipikas', ' None'])
with open('Juulius.csv', 'r') as f: # Avame ja loeme:
sisu = f.read()
print(sisu)
No, Name, Contribution 1, Linus Torvalds, Linux Kernel 2, Tim Berners-Lee, World Wide Web 3, Guido van Rossum, Python Programming 4, Juulius Tipikas, None
5.1.2 Funktsioon csv.reader¶
Mooduli csv funktsioon reader väljastab failiobjekti mida saame lugeda:
import csv
with open('Juulius.csv', 'r') as f: # Loeb ka muid faililaiendeid.
reader = csv.reader(f)
for row in reader: # reader, iteraatortoega objekt.
print(row)
['No', ' Name', ' Contribution'] ['1', ' Linus Torvalds', ' Linux Kernel'] ['2', ' Tim Berners-Lee', ' World Wide Web'] ['3', ' Guido van Rossum', ' Python Programming'] ['4', ' Juulius Tipikas', ' None']
Funktsiooni csv.reader valitud argumentide kasutus:
import csv
with open('Juulius.csv', 'r') as f:
reader = csv.reader(f, skipinitialspace=True) # Eemaldab tühikud.
for row in reader:
print(row)
['No', 'Name', 'Contribution'] ['1', 'Linus Torvalds', 'Linux Kernel'] ['2', 'Tim Berners-Lee', 'World Wide Web'] ['3', 'Guido van Rossum', 'Python Programming'] ['4', 'Juulius Tipikas', 'None']
5.1.3 Klass csv.DictReader¶
Eelnevalt kasutatud CSV faili ridade põhjal saab luua sõnaraamatuid. Klass csv.DictReader loob objekti mis käitub sarnaselt csv.reader poolt loodud objektile. Klassi kasutus ja selle poolt loodud sõnastike kuju:
import csv
with open("Juulius.csv", 'r') as f:
csv_file = csv.DictReader(f, skipinitialspace=True)
for sonastik in csv_file:
print(sonastik) # Võid muuta tavaliseks sõnastikuks, dict(sonastik).
print()
with open("Juulius.csv", 'r') as f:
csv_file = csv.DictReader(f, skipinitialspace=True)
for sonastik2 in csv_file:
print(dict(sonastik2))
sonastik2['Name']
{'No': '1', 'Name': 'Linus Torvalds', 'Contribution': 'Linux Kernel'}
{'No': '2', 'Name': 'Tim Berners-Lee', 'Contribution': 'World Wide Web'}
{'No': '3', 'Name': 'Guido van Rossum', 'Contribution': 'Python Programming'}
{'No': '4', 'Name': 'Juulius Tipikas', 'Contribution': 'None'}
{'No': '1', 'Name': 'Linus Torvalds', 'Contribution': 'Linux Kernel'}
{'No': '2', 'Name': 'Tim Berners-Lee', 'Contribution': 'World Wide Web'}
{'No': '3', 'Name': 'Guido van Rossum', 'Contribution': 'Python Programming'}
{'No': '4', 'Name': 'Juulius Tipikas', 'Contribution': 'None'}
'Juulius Tipikas'
5.1.4 Klass csv.DictWriter¶
Klass DictWriter loob objekte mis käituvad nagu csv.writer objektid. Kasutuse näide:
import csv
with open('Juulius.csv', 'w') as f:
päis = ['Nimi', 'Kool']
writer = csv.DictWriter(f, fieldnames=päis)
writer.writeheader() # Päise loomine.
writer.writerow({'Nimi': 'Juulius Tipikas', 'Kool': 'TPI'})
writer.writerow({'Nimi': 'Juhan Liiv', 'Kool': 'TTÜ'})
with open('Juulius.csv', 'r') as f:
sisu = f.read()
print(sisu)
Nimi,Kool Juulius Tipikas,TPI Juhan Liiv,TTÜ
5.2 Teek NumPy¶
Teadusarvutuste tegemiseks kasutatakse sageli populaarset teeki NumPy. NumPy võimaldab CVS tüüpi tekstifailidega töötamise.
5.2.1 Funktsioon numpy.savetxt¶
Funktsiooni numpy.savetxt kasutame andmete salvestamiseks:
from numpy import savetxt
time = [1, 2, 3]
data = [1.7, 1.8, 1.9]
savetxt('Juulius.txt', (time, data), delimiter=',')
with open('Juulius.txt', 'r') as f:
sisu = f.read()
print(sisu)
1.000000000000000000e+00,2.000000000000000000e+00,3.000000000000000000e+00 1.699999999999999956e+00,1.800000000000000044e+00,1.899999999999999911e+00
Kui soovid listid salvestada vertikaalselt tulpadesse:
import numpy as np
time = [1, 2, 3]
data = [1.7, 1.8, 1.9]
structured = np.column_stack((time, data))
#structured = np.array([time, data]).T # Transponeerime masiivi, nii saab ka.
np.savetxt('Juulius.txt', structured, delimiter=';')
with open('Juulius.txt', 'r') as f:
sisu = f.read()
print(sisu)
1.000000000000000000e+00;1.699999999999999956e+00 2.000000000000000000e+00;1.800000000000000044e+00 3.000000000000000000e+00;1.899999999999999911e+00
5.2.2 Funktsioon numpy.loadtxt¶
Funktsiooni numpy.loadtxt kasutame andmete lugemiseks. Oletame, et meil on mitme tulbaga fail mis sisaldab numbreid. Moodul NumPy sisaldab funktsiooni mis lubab need andmed suhteliselt lihtsalt sisse lugeda. Lisainfo: https://numpy.org/doc/stable/reference/generated/numpy.loadtxt.html
from numpy import loadtxt
v1, v2 = loadtxt('Juulius.txt',
delimiter = ';',
skiprows = 0,
usecols = (0, 1),
unpack = True)
print(v1, v2)
[1. 2. 3.] [1.7 1.8 1.9]
from numpy import loadtxt
from io import StringIO
fail = StringIO("0 1 2\n2 3 4") # Käitub nagu failiobjekt, failise on 3 tulpa ja 2 rida.
v1, v2 = loadtxt(fail,
delimiter = ' ',
skiprows = 0,
usecols = (1, 2), # Kasutan ainult neid tulpasid.
unpack = True)
print(v1, v2)
[1. 3.] [2. 4.]
Kasutus koos kontekstihalduriga ehk with-plokis:
with StringIO("0 1 2\n2 3 4") as f: # Väljakutse StringIO() asemel kasuta faili nime ja laiendit.
v1, v2 = loadtxt(f,
delimiter = ' ',
skiprows = 0,
usecols = (1, 2), # Kasutan ainult neid tulpasid.
unpack = True)
print(v1, v2)
[1. 3.] [2. 4.]
5.2.3 Funktsioon numpy.genfromtxt¶
Funktsiooni numpy.genfromtxt kasutame andmete lugemiseks. Erinevus võrreldes funktsiooniga numpy.loadtxt on see, et numpy.genfromtxt võimaldab faili lugeda ka siis kui see sisaldab puuduvaid või vigaseid andmeid.
Loeme sisse faili Juulius.txt:
import numpy as np
txt = np.genfromtxt('Juulius.txt', dtype=None, delimiter=';')
print(txt)
[[1. 1.7] [2. 1.8] [3. 1.9]]
Näide andmetest mis on puudulikud:
import numpy as np
from io import StringIO
data_str = """Name,Age,Height
Alice,25,165
Bob,,180
Charlie,30,
,28,175
"""
data = StringIO(data_str)
arr = np.genfromtxt(data,
delimiter=",",
names=True,
dtype=[('Name', 'U10'), ('Age', 'f8'), ('Height', 'f8')],
encoding="utf-8",
missing_values="",
filling_values=np.nan)
print(arr)
[('Alice', 25., 165.) ('Bob', nan, 180.) ('Charlie', 30., nan)
('', 28., 175.)]
6 NumPy andmemasiivide numpy.ndarray serialiseerimine¶
Teek NumPy võimaldab salvestada andmemassiivi numpy.ndarray (käsitleme järgmistes loengutes) talletatud väärtusi binaarsesse, serialiseeritud faili. Salvestatud masiivi faili laiend on .npy. Mitme massiivi koos salvestamiseks kasutatakse laiendit .npz.
import numpy as np
with open('Juulius.npy', 'wb') as f: # Loome binaarse faili.
np.save(f, np.array([1, 2])) # Salvestame andmemasiivi.
np.save(f, np.array([3, 4]))
with open('Juulius.npy', 'rb') as f: # Loeme faili. Fail sisaldab kõike vajalikku objekti taastamiseks.
a = np.load(f) # Loodud .npy ja .npz failide lugemiseks.
b = np.load(f)
print(a, b)
[1 2] [3 4]
Lisaks võid vaadata ka funktsioone numpy.savez ja numpy.savez_compressed.
7 Muude teksti ja binaarsete failidega töötamine Pythonis¶
Soovitus õpi kasutama teeki pandas. Teek on Anaconda installatsiooniga kaasas.
7.1 Teegi pandas ülevaade¶
Teek pandas on Pythoni teek, mis pakub kiireid, paindlikke ja väljendusrikkaid andmestruktuure, mis on loodud selleks, et "relatsiooniliste" või "sildistatud" andmetega töötamine oleks lihtne ja intuitiivne. Selle eesmärk on olla peamine kõrgtaseme ehitusplokk praktilise ja reaalse andmeanalüüsi tegemiseks Pythonis.
Teek pandas sobib hästi paljude erinevat tüüpi andmete jaoks:
- Tabelandmed, mille veerud on erinevat tüüpi, nagu SQL-tabelis või Exceli arvutustabelis
- Järjestatud ja järjestamata (mitte tingimata fikseeritud sagedusega) aegridade andmed
- Suvalised maatriksandmed (üht tüüpi või erinevat tüüpi), millel on rea- ja veerusildid
- Mis tahes muu tüüpi vaatlus- või statistilised andmekogumid. Andmed ei pea olema sildistatud, et neid saaks pandas’e andmestruktuuris kasutada.
Loe lisaks: https://pandas.pydata.org/pandas-docs/stable/getting_started/overview.html
8 Mooduli muutujatele väärtuste omistamine konsoolist (argument parsing)¶
Loome mooduli proge.py mis sisaldab järgmist lähtekoodi:
import sys
x = int(sys.argv[1])
y = int(sys.argv[2])
print('Argumente kokku: {}'.format(len(sys.argv)))
print('Edastatud argumendid: {}'.format(sys.argv))
print('x + y =', x + y)
Käivita programm konsoolist kasutades käsku python proge.py 5 6, kus 5 ja 6 on muutujatele x ja y edastatud (parsitud) väärtused.
Allolev tabel seletab argumentide sys.argv indekreesimise järjekorda.
| python | proge.py | <argument 1> | <argument 2> |
|---|---|---|---|
| indeks | 0 | 1 | 2 |