8 Skrár¶
8.1 Yfirlit¶
Langtímageymslur
Til að geyma gögn til lengri tíma en rétt á meðan forrit er að keyra eru yfirleitt notaðar skrár (files). Þær eru oft geymdar á svonefndum hörðum diski (hard disk), sem er búinn til úr þunnum segulmögnuðum skífum sem snúast á miklum hraða í diskdrifi. Nú til dags eru reyndar gagnageymslur með leifturminni (flash drive, solid state drive, SSD) orðnar algengar. Lesandi sem vill kynna sér svona geymslur betur verður að leita út fyrir þessar fyrirlestrarnótur, því hér höldum við okkur við hugbúnaðarhliðina (software).
Staðsetningar skráa
Með Python er hægt að lesa gögn úr skrá inn í minni tölvunnar, og það er líka hægt að skrifa út í skrár. Skráin getur verið hvort sem er á diski tölvunnar eða úti á vefnum (þá bara til að lesa), og þriðji möguleikinn er að skráin sé í skýinu, og það á sér í lagi við þegar Python keyrir á tölvu í skýinu, eins og raunin er þegar Google Colab er notað.
Skráategundir
Eins og flestir lesendur vita væntanlega geta skrár líka verið með ýmsu sniði, og stundum eru skrárnar kallaðar skjöl (documents). Nokkur dæmi eru textaskrár, Word-skjöl, Excel-skjöl, myndaskrár og PDF-skjöl. Til að byrja með gera þessar nótur ráð fyrir að skrárnar séu staðsettar á beint aðgengilegum stað, annaðhvort á vefnum eða í svonefndri sjálfgefinni möppu, en í kafla 8.5 verða aðrir möguleikar skoðaðir.
Nöfn skráa
Skrár heita langoftast einhverju nafni sem er textastrengur. Það eru mun minni
takmarkanir á nöfnum skráa en á breytunöfnum: skráanöfn mega innihalda ýmis
sértákn, og t.d. er algengt að nota –, :, . og bil, auk bókstafa og
tölustafa. Það er samt ekki hægt að nota skástrik, hvorki / né \. Reyndar geta
séríslenskir stafir valdið vandræðum. Á það á til dæmis við ef skrám er er
hlaðið upp til notkunar í Google Colab :(. Skráanöfn eru oft með sniðinu
aðalnafn.undirnafn
(basename.extension) þar sem .undirnafn segir til um
tegund skrárinnar og getur t.d. verið .txt
fyrir textaskrár, .xlsx
fyrir
Excel-skjöl og .png
fyrir myndir á png-sniði. Dæmi um skráanöfn eru:
gögn 14.09.2021 14:59:00.txt
skiladæmi-12.pdf
.
Reyndar er það svo á bæði Windows-tölvum og Mökkum að sjálfgefið er að undirnafnið sé falið. Tegund skrárinnar er þá sýnd með öðrum hætti, oft bæði með teikni (icon) og textalýsingu, sbr. mynd 8.3, þar sem tölvan hefur reyndar verið stillt á að fela undirnafnið ekki.
Pakkar til að lesa og skrifa skrár
Það eru ýmsar leiðir til að lesa og skrifa skrár í Python. Hefðbundna aðferðin
er að nota innbyggðu föllin open
, read
og write
(og reyndar nokkur
skyld föll), sem einkum nýtast fyrir textaskrár. Stundum eru skrárnar sniðnar á
ákveðinn hátt, til dæmis með því að aðskilja dálka með kommum, semíkommum eða
tab-táknum, og þá gæti pakkinn csv
(comma-separated-values) hentað.
Pakkasöfnin Pandas og Numpy sem rædd voru í kafla 10.1 eru
með sín föll til að lesa skrár, og svo eru til sérstakir pakkar til að lesa
ýmsar sérsniðnar skrár t.d. Excel-skjöl og myndaskrár. Loks má nefna pakkann
pathlib sem er á dagskrá í kafla 8.5.
8.2 Innlestur skráa¶
8.2.1 Línuskiptatákn¶
Áður en hefðbundinn innlestur skráa verður útskýrður þarf að segja nokkur orð um
línuskiptatákn (line feed, line break eða newline character), sem er
notaður til að fara í nýja línu í textaskrá. Hann er kóðaður með tölunni 10 og
oft táknaður með stafasamstæðunni \n
, m.a. í Python. Það er líka hægt að
nota hann í print
-köllum, t.d.
print(x, y, sep="\n") # prentar x og y hvort á sína línuna
print(f"x = {x}\ny = {y}") # prentar líka á tvær línur).
8.2.2 With-skipun¶
Annað atriði sem þarf að ræða áður en við hellum okkur í innlesturinn er with-skipun. Hún er notuð til að einfalda forrit þar sem par af skipunum umlykur skipanablokk. Þetta virkar svona:
with BYRJUN(...) as v v = BYRJUN(...)
skipanablokk jafngildir: skipanablokk
... LOKASKIPUN
...
Til að þetta virki þarf fallið BYRJUN að vera samhæft við notkun with-skipunar,
þannig að það sjái líka um lokaskipunina, sem framkvæmist þá sjálfkrafa þegar komið er
út úr with-blokkinni. With-skipunin hefur annan kost, að ef skipanablokkin
inniheldur einhverjar skipanir sem brjótast út úr henni (return
, break
eða continue
) þá missum við af lokaskipununum með forritsbútnum hægra megin,
en ekki ef við notum with. Nánar tiltekið:
with BYRJUN(...) as v v = BYRJUN(...)
skipanir1 skipanir1
if skilyrði: jafngildir: if skilyrði:
return LOKASKIPUN
skipanir2 return
... skipanir2
LOKASKIPUN
...
Einföldunin er sem sé orðin umtalsverð.
8.2.3 Hefðbundinn innlestur textaskrár af diski¶
Til að lesa úr textaskrá þarf fyrst að opna hana með open og eftir innlesturinn þarf að loka henni með close. Hinsvegar eru open–close einmitt par af skipunum BYRJUN–LOKASKIPUN sem eru samhæfðar við with. Hefðin er sú að nota with-skipun með open, og þessar fyrirlestrarnótur miðast við það.
Python hefur þrjú innbyggð föll til að lesa textaskrá, readline, readlines og read. Fyrsta fallið les eina línu úr skránni inn í streng, næsta fall les allar línur sem eftir er að lesa inn í lista af strengjum og það þriðja les alla skrána inn í einn streng. Í öllum tilfellum eru línuskiptatákn aftast í hverjum lesnum streng.
Sýnidæmi: Lestur skrár
Gerum ráð fyrir að skráin data.txt
innihaldi:
Nafn Hæð
Bára 171
Jóna 168
Kári 178
og eftirfarandi forritsbútur sé framkvæmdur:
with open("data.txt") as f:
hauslína = f.readline()
línur = f.readlines()
with open("data.txt") as f:
skráin = f.read()
Þá verður hauslína strengurinn "Nafn Hæð\n"
, línur
verður listinn
["Bára 171\n", "Jóna 168\n", "Kári 178\n"]
, og skráin
verður
strengurinn "Nafn Hæð\nBára 171\nJóna 168\nKári 178\n"
Takið eftir að það þarf að opna skrána aftur áður en kallað er á read.
Til að losna við línuskiptatákn aftast í streng má nota fallið strip()
.
Þetta fall hentar ágætlega þegar skrá er lesin línu fyrir línu, og eitthvað gert
við hverja línu, eins og gert er í næsta sýnidæmi sem prentar línurnar. Dæmið
nýtir sér að hægt er að nota opnaðar Python-skrár sem ítrara. Fallið next
nær í fremsta gildi ítrara, og stillir hann samtímis þannig að næst skili hann
afgangi gilda sinna.
Sýnidæmi: Skrá lesin og prentuð
Hér er forrit sem les línur skrár hverja á fætur annarri og prentar þær út. Byrjað er á að lesa hauslínuna sér.
with open("data.txt") as f:
hauslína = next(f).strip()
print("Hauslína:, hauslína")
print("Aðrar línur:")
for lína in f:
strengur = lína.strip()
print(strengur)
Forritið prentar:
Hauslína: Nafn Hæð
Aðrar línur:
Bára 171
Jóna 168
Kári 178
Þegar skrá er lesin öll í einu með read
er hægt að nota splitlines
til
að losna við línuskiptatáknin, svona:
with open("data.txt") as f:
L = f.read().splitlines()
# Nú er L listinn ['Nafn Hæð', 'Bára 171', 'Jóna 168', 'Kári 178']
Æfing: Textaskrá lesin inn
Búið til skrána „data.txt“ á tölvunni ykkar með innihaldinu sem gefið er í sýnidæminu „Lestur skrár“ að ofan. Á Windows má opna File Explorer, fara t.d. í möppuna Documents, hægri smella og velja New–Text Document. Síðan má tvísmella á skrána, slá inn texta og velja að lokum File–Save. Á Makka má smella á command–space, slá inn TextEdit og enter. Síðan er valið Format–Make Plain Text. Þá er texti skrárinnar sleginn inn, valið File–Save og skránni loks valinn staður, t.d. í Documents möppu.
Þið ráðið hvort þið leysið þennan lið í Colab eða JupyterLab.
Í Colab: Farið nú í Google Colab og opnið nýja vinnubók. Smellið á möpputáknið í vinstri spássíu og þvínæst upphleðslutáknið sem birtist og hlaðið upp nýju skránni,
data.txt
. Smellið á hana til að skoða innihaldið og staðfestið að allt sé rétt.Í JupyterLab Opnið JupyterLab í möppunni þar sem skránni var valinn staður í lið 1 og búið til nýja vinnubók.
Skrifið nú forrit sem les skrána og prentar hana jafnóðum út, eins og gert er í seinna sýnidæminu að ofan, nema hvað ekki á að meðhöndla hauslínuna sérstaklega.
8.2.4 Innlestur textaskrár af vefnum¶
Hægt er að lesa textaskrá beint af vefnum ef hún er opnuð með fallinu urlopen sem er í pakkanum urllib.request. Ekki þarf að loka slíkri skrá eftir notkun svo það er engin þörf á with-skipun. Hinsvegar eru strengir sem eru lesnir úr skrá á vefnum ekki sjálfkrafa kóðaðir í Python-strengi heldur helst snið þeirra, og það er nánast alltaf svonefnt „utf-8“ snið. Til að fá rétta Python-strengi þarf að beita fallinu decode().
Hér fylgir sýnidæmi um svona innlestur, sem sýnir líka hvernig hægt er að ná í
einstök atriði í hverri línu með split
fallinu. Það losar okkur í leiðinni
við línuskiptatáknin og gerir þar með strip()
óþarft. Mörg fleiri dæmi um
lestur skráa af vefnum eru í verkefnunum aftast í þessum fyrirlestrarnótum.
Sýnidæmi: Skrá lesin af vefnum
Skráin sem notuð var í sýnidæmunum hér á undan hefur verið sett á vefinn, í https://cs.hi.is/python/data.txt. Hér er hún lesin inn í tvo lista sem svo eru prentaðir út. Listarnir byrja tómir og svo lengjast þeir í hverri umferð for-lykkjunnar. Við notum tækifærið og sýnum samspil enumerate og zip, sbr. æfingu afast í kafla 5.6.
from urllib.request import urlopen
f = urlopen("https://cs.hi.is/python/data.txt")
nöfn = []
hæðir = []
for lína in f:
(nafn,hæð) = lína.decode().split()
nöfn.append(nafn)
hæðir.append(hæð)
for nr,(n,h) in enumerate(zip(nöfn, hæðir)):
print(f"{nr}: {n} {h}")
Út prentast:
0: Nafn Hæð
1: Bára 171
2: Jóna 168
3: Kári 178
8.2.5 Uppflettitafla lesin úr skrá¶
Í sýnidæminu hér næst á undan var gagnaskrá lesin inn í tvo lista, en oft hentar betur að vinna með gögn í uppflettitöflum. Sýnidæmin hér á eftir sýnir tvo möguleika á að ná uppflettitöflu úr skrá: (a) að búa töfluna til samhliða innlestrinum, og (b) að lesa inn í tvo lista sem svo er breytt í uppflettitöflu. Notast er við sömu skrá og síðast.
Sýnidæmi: Uppflettitafla samhliða innlestri
Nöfnin verða lyklar í uppflettitöflunni sem búin er til og hæðirnar gildi. Að
loknum innlestri er taflan prentuð. Takið eftir hvernig items
er notað
til að renna samhliða í gegn um pör nafna og hæða.
from urllib.request import urlopen
f = urlopen("https://cs.hi.is/python/data.txt")
tafla = {}
for lína in f:
(nafn,hæð) = lína.decode().split()
tafla[nafn] = hæð
for (nafn,hæð) in tafla.items():
print(f"{nafn} {hæð}"
Út prentast:
Nafn Hæð
Bára 171
Jóna 168
Kári 178
Sýnidæmi: Uppflettitafla eftir innlestur
Við byrjum að keyra fyrstu átta línurnar í forritinu í sýnidæmi Skrá lesin af vefnum í kaflanum á undan og fá þannig tvo lista Síðan búum við töfluna til með aðstoð dict og zip og prentum hana út eins og fyrr:
tafla = dict(zip(nöfn,hæðir))
for (nafn,hæð) in tafla.items():
print(f"{nafn} {hæð}"
Æfing: Prófnúmer og einkunnir
Skráin https://cs.hi.is/python/profnumer.txt inniheldur tvo dálka, prófnúmer og skírnarnafn. Lesið þessa skrá inn í uppflettitöflu, prófnúmer \(\to\) nafn,
með því að byrja með tóma töflu og bæta við hana samhliða innlestri, eins og í fyrra sýnidæminu að framan, og
með því að lesa inn tvo lista og nota
dict(zip(...))
eftir innlesturinn, eins og í seinna sýnidæminu.Gunnar íslenskukennari notaði prófnúmer þegar hann fór yfir ritgerðir (svo hann yrði ekki hlutdrægur). Hér eru einkunnirnar sem hann gaf:
prófnúmer: 176, 542, 1577, 2785, 4218, 6354, 8003, 9134 einkunn: 8.5, 10.0, 4.5, 9.0, 7.5, 6.0, 8.5, 8.0Skrifið forrit sem býr til tvo lista úr þessum upplýsingum, flettir upp á nöfnum í uppflettitöflunni og býr til einkunnalista sem byrjar svona:
Nemandi Prófnúmer Einkunn –––––––––––––––––––––––––––––– Kjartan 0176 8.5 Aðalheiður 0542 10.0 Hulda 1577 4.5 ...Athugasemd:
Ef sýnidæmunum að framan er fylgt verða prófnúmerin sjálfkrafa strengir, en listinn í c-lið gefur heiltölur. Til að komast hjá þessu ósamræmi mætti breyta prófnúmerinu í tölu eftir að það er lesið inn úr skránni, t.d. með
prófnr = int(prófnr)
. Til að prenta 0 fremst í prófnúmerum í lokatöflunni má svo nota f-streng með sniði{...:04}
sbr. töflu 4.1.
8.3 CSV-skrár¶
Gögnum í skrám er oft skipað í dálka, t.d. nöfn í fyrsta dálki, símanúmer í 2. dálki og heimilisföng í 3. dálki. Það eru ýmsar leiðir notaðar til að afmarka dálkana: Stundum eru dálkarnir af fastri breidd, en stundum eru þeir afmarkaðir með sérstöku afmörkunartákni (delmiter), oftast kommu, semikommu (;), tab-tákni eða bilum. Skrár sem nota kommu eða semikommu eru kallaðar CSV-skrár (comma separated values) og slíkar skrár er auðvelt að búa til með Excel.
8.3.1 Dæmi um CSV-skrá¶
Hér er dæmi um símaskrá sem notar semíkommu til að afmarka dálka:
NAFN; SÍMI; HEIMILI
Jón Jónsson; 8883333; Geiragötu 18, Reykjavík
Ása Bára Jónsdóttir;7772222; Unugötu 3, Akureyri
Ari Arason; 5551111; Arastíg 1, Selfossi
Það væri líka hægt að nota tab-tákn til að afmarka, en kommur eða bil mundu síður henta því einstök atriði (svið; fields) í skránni innihalda bæði kommur og bil. Sá sem sló inn þessa skrá var ekki mikið að hugsa um samræmi, það er allur gangur á því hvort eitt eða fleiri bil koma á eftir semíkommunum, en við sjáum í næsta kafla að það kemur ekki að sök.
Í Wikipedíugrein um CSV-skrár eru fleiri dæmi t.d. í kaflanum Example. Þar er m.a. rætt hvernig hægt er að geyma svið sem innihalda bil með því að slá gæsalöppum utan um þau, en við förum ekki nánar út í þá sálma hér.
8.3.2 Innlestur með pakkanum csv¶
Til að lesa skrá sem afmarkar dálka með sérstöku tákni eða bilum inn í Python
hentar ágætlega að nota pakkann csv
. Með honum er notað with open
alveg
eins og gert er í kafla 8.2.3, síðan er búinn til
svonefndur lesari (hlutur af taginu csv_reader
) og hann loks notaður til að
lesa, sbr. eftirfarandi dæmi.
Sýnidæmi: CSV-skrá lesin
Gerum ráð fyrir að skráin í kafla 8.3.1 sé geymd í
simaskra.txt
. Eftirfarandi forrit mundi lesa hana inn og prenta á skjá:
import csv
with open("simaskra.txt") as f:
reader = csv.reader(f, delimiter=';', skipinitialspace=True)
for röð in reader:
print(f"{röð[0]:20} {röð[1]:7} {röð[2]}")
Við sjáum að lesarinn reader er ítrari sem skilar lista með atriðum hverrar
línu þegar hann er notaður í for-setningu. Viðfangið skipinitalspace=True
sér til þess að bilunum sem koma aftan við semíkommurnar (þ.e. fremst í
hverju sviði) sé sleppt. Forritið mundi prenta út:
NAFN SÍMI HEIMILI
Jón Jónsson 8883333 Geiragötu 18, Reykjavík
Ása Bára Jónsdóttir 7772222 Unugötu 3, Akureyri
Ari Arason 5551111 Aragötu 1, Selfossi
Komma er sjálfgefið afmörkunartákn. Skrá sem er afmörkuð með tab-táknum má lesa
með delimiter="\t"
. Ef sleppa ætti innlestri á fyrirsagnarlínunni mætti
skrifa next(reader)
næst á undan for-lykkjunni.
8.3.3 CSV-lestur úr lista af strengjum¶
Ef gefinn er listi af strengjum sem hver um sig inniheldur svið afmörkuð með kommum eða öðrum táknum þá er hægt að nota csv-pakkann til að ná í þessi svið alveg eins og um væri að ræða línur í skrá. Hér er einfalt dæmi:
línur = ["grænn, 0.1, 0.6, 0.1", "blár, 0, 0.2, 0.9", "gulur, 1, 0.9, 0"]
rdr = csv.reader(línur, skipinitialspace=True)
for L in rdr:
print(L)
sem prentar út:
['grænn', '0.1', '0.6', '0.1']
['blár', '0', '0.2', '0.9']
['gulur', '1', '0.9', '0']
Æfing: Verð mjólkurlítra
Lesið eftirfarandi verðlista og prentið hann út sem töflu:
[["Nýmjólk;177", "Léttmjólk;179", "Fjörmjólk;219"]]
8.3.4 CSV-skrá lesin af vefnum¶
Símaskrána í kafla 8.3.2 má finna í https://cs.hi.is/python/simaskra.txt. Til að lesa þessa skrá beint af netinu með csv-lesara þarf að fara krókaleið og lesa fyrst líkt og gert er í fyrra sýnidæminu í kafla 8.2.3 áður en lesaranum er beitt á strengjalistann sem kemur út úr því. Hér er forritsbútur sem útfærir þetta:
url = "https://cs.hi.is/python/simaskra.txt"
import csv
from urllib.request import urlopen
f = urlopen(url)
lines = [l.decode() for l in f.readlines()]
reader = csv.reader(lines, delimiter=';', skipinitialspace=True)
for (nafn, sími, heimili) in reader:
print(f'{nafn:19} {sími:7} {heimili:20}')
8.3.5 Skrár afmarkaðar með bilum¶
Ef ekkert atriði inniheldur bil má nota bil til að afmarka dálkana. Á ensku er talað um whitespace-delimited file. Algengt er að nota eitt eða fleiri bil milli dálka og láta þá standast á.
Sýnidæmi: Bilaafmörkuð skrá
Lát skrána malmar.txt innihalda:
Málmur Eðlisþyngd Bræðslumark
Ál 2.70 933
Járn 7.87 1538
Kopar 8.96 1085
Gull 19.30 1064
Eftirfarandi forritsbútur mundi lesa skrána:
import csv
with open("malmar.txt") as f
reader = csv.reader(f, delimiter=' ', skipinitialspace=True)
next(reader) # titillína lesin (og henni hent)
for lína in reader:
málmur = lína[0]
eðlisþ = float(lína[1])
bræðslum = int(lína[2])
...
Þessi skrá verður notuð í verkefni 17
8.3.6 Náð í dálk í CSV-skrá¶
Ef búið er að búa til lesara rdr = csv.reader(...)
eins og í sýnidæmunum í
köflum 8.3.2 og 8.3.4 þá má breyta honum
í lista af listum sem hver geymir upplýsingar úr einni línu skrárinnar með því
að skrifa:
L = list(rdr)
Hér notum við að rdr
er ítrari, og fallið list
úr kafla
6.1 býr til lista úr honum. Svo má nota yfirgrip til að ná til dæmis í
stak nr. 1 í öllum undirlistunum í L svona:
dálkur1 = [undirlisti[1] for undirlisti in L]
eða bara d1 = [x[1] for x in L]
. Ef dálkurinn inniheldur kommutölur má ná
í lista af þeim með d1 = [float(x[1]) for x in L]
.
8.4 Skrár skrifaðar út¶
Til að skrifa í textaskrá þarf að opna hana í útskriftarham með því að rita
with open("skráarnafn", mode="w") as file:
Reyndar má sleppa mode= og rita open("skráarnafn", "w")
. Skráin lendir
sjálfkrafa í núverandi möppu. Síðan má nota fallið write
til að skrifa
strengi í skrána en þess þarf að gæta að setja handvirkt línuskiptatákn
aftast í hverja línu.
Sýnidæmi: Skráaskrift með write
Forrit sem býr til skrá xy.dat
með strengjunum „x=3“ og „y=4“. Takið eftir að
hægt er að skrifa f-strengi með write.
with open("xy.dat", "w") as f:
(x,y) = (3,4)
f.write("x = {x}\n")
f.write("y = {y}\n")
Það er líka hægt að nota print
til að skrifa í skrár með því að hafa
viðfangið file = f
með, og þá koma línuskiptin sjálfkrafa með, sbr.
eftirfarandi dæmi
Sýnidæmi: Skráaskrift með print
Eftirfarandi forrit býr til eins skrá og dæmið að framan.
with open("xy1.dat", "w") as f:
(x,y) = (6,7)
print(f"x = {x}", file=f)
print(f"y = {y}", file=f)
Æfing: Skráaskrift úr vinnubók
Afritið forritin í sýnidæmunum tveimur hér að framan inn í reiti í vinnubók og keyrið þau. Skoðið svo skrárnar sem urðu til [í Colab má smella á möpputáknið í vinstri spássíu, en á eigin tölvu má nota Finder (Mac) eða File Explorer (Windows)].
8.5 Skráakerfi¶
Tölvuskrár eru oftast settar upp í svonefnt skráakerfi (file system). Gögnum er skipað í skrár sem hver hefur sitt nafn, og síðan er skrám skipað í möppur (folders, directories), líka hver með sínu nafni. Fyrir utan skrár geta möppur innihaldið aðrar möppur, sem eru þá kallaðar undirmöppur (subfolder, subdirectory) en mappan sem inniheldur þær er yfirmappa (parent folder).
8.5.1 Möpputré¶
Möppum er oft raðað saman í kerfi sem er eins og tré á hvolfi, en kerfið er líka stundum sýnt með því að lista innihald möppu inndregið fyrir neðan nafn möppunnar. Hér eru tvö dæmi:
Í fyrra dæminu eru bara hluti af möppum á tölvunni sýndar, þær sem tilheyra tilteknum notanda. En stór hluti af skrám á tölvu tilheyra stýrikerfinu og ýmsum hugbúnaði (applications) sem er uppsettur á henni. Síðara dæmið sýnir hluta af skráakerfi á Makka höfundar þar á meðal ýmsar slíkar stýrikerfisskrár, en líka heimamöppu hans (jonasson) og tvær undirmöppur hennar.
Oft er eitt svona möpputré fyrir hvern disk á tölvunni, og ef maður stingur USB-kubbi í hana sýnir hún sérstakt tré fyrir hann. Ef Google drive eða Dropbox eru notuð eru líka sérstök möpputré fyrir þau. Efsta mappan í svona möpputré er kölluð rót (root) eða rótarmappa. Á Linux og Mökkum er rótarmappan táknuð með „/“ en á Windows gjarna með „C:". En þetta er ekki algilt, t.d. sýnir Finder (=*File Explorer*) rótarmöppuna á Makka höfundar undir heitinu Macintosh HD.
8.5.2 Heimamappa¶
Á flestum tölvum á hver notandi sína heimamöppu, sem heitir nafni sem er líka notendanafn hans. Á Mökkum og Windows-tölvum er kerfið oft sett þannig upp að undir rótarmöppu tölvunnar er mappa Users, og undir henni eru heimamöppur þeirra notenda sem hafa verið settir upp. Í heimamöppunum eru síðan möppurnar Documents, Downloads, Desktop, Pictures, Music o.fl. Í Ubuntu Linux heitir yfirmappa heimamöppunnar home en ekki Users.
8.5.3 Núverandi mappa¶
Þegar forrit keyrir er það oftast statt í tiltekinni möppu sem kölluð er sjálfgefin mappa eða núverandi mappa (current working directory). Þetta er sú mappa sem skrár lenda í þegar þær eru vistaðar úr forritinu, og líka sú þar sem fyrst er leitað að skrá til að opna. Oft er það heimamappan sem er sú sjálfgefna, eða þá mappan Documents, nema um sé að ræða myndvinnsluforrit eða tónlistarforrit t.d.
Það gildir líka um Python-forrit notanda að það er statt í tiltekinni möppu þegar það keyrir. Þegar JupyterLab er keyrt upp frá skipanalínu í ákveðinni möppu þá er forritið í byrjun statt þar. En þegar keyrt er með Google Colab þá er maður staddur á einhverri tölvu uppi í Skýinu, nánar tiltekið í möppu sem heitir „/content“. Það er hægt að skoða skráakerfi þessarar tölvu með því að smella á möpputáknið í vinstri spássíu gluggans. Þá birtast líka hnappar til að hlaða upp eða niður skrám frá/á eigin tölvu og sömuleiðis er hægt að tengja Google Drive notanda við þetta skráakerfi.
8.5.4 Slóðir¶
Þegar vísað er í skrá er hægt að gera það með því að gefa upp svonefnda slóð
(path) skrárinnar, en það er runa af möppum sem sýnir hvar skráin er, aðskilin
með skástrikum, sem endar á skránni sjálfri. Svo er líka talað um slóð möppu,
sem endar þá á möppunafninu. Sérstaka möppunafnið ..
táknar yfirmöppu, þ.e.
að farið sé upp tréð. Slíka slóð má gefa upp miðað við rót trésins (algild
slóð, absolute path), og þá er byrjað á /
, eða miðað við núverandi möppu
(afstæð slóð, relative path), og þá byrjar slóðin ekki á /
. Stundum er
líka notað sérstaka möppunafnið .
sem táknar núverandi möppu.
Sýnidæmi: Slóðir
Notandi sem er staddur í möppunni Old neðst til hægri á mynd 8.4 getur vísað í skrána Two.txt á sömu mynd með slóðinni
../../Data/Two.txt
Notandi sem er staddur í möppunni Downloads á mynd 8.5 getur vísað í skrána listi.xlsx hvort sem er með
/Users/jonasson/Documents/listi.xlsx
eða../Documents/listi.xlsx
.Mappan Downloads á mynd 8.5 hefur slóð
/Users/jonasson/Downloads
.
8.5.5 Einingin pathlib¶
Í (eldri) Python-forritum er algengt að notuð sé einingin os (operating system) til að meðhöndla möppur og slóðir. Einingin pathlib er nýleg og tilgangur hennar er að leysa os af hólmi með einfaldari aðgerðum. Hér lýsum við bara hvernig nota má pathlib, en nefna má að Think Python-bókin útskýrir os-eininguna í kafla 14.4.
Mikilvægasta fallið í pathlib er kallað Path
og það er virkjað með því að
rita:
from pathlib import Path
Við algengustu notkun tekur Path einn stika sem er slóð á strengjaformi,
annaðhvort afstæð eða algild, og það skilar hlut af taginu PosixPath sem er í
rauninni gagnatag fyrir slóð. Sjálfgefið gildi stikans er .
þ.e.a.s.
núverandi mappa. Hlutur af taginu PosixPath hefur ýmsar aðferðir, og eru
nokkrar þær helstu sýndar í næstu töflu, sem miðast við að Path-hluturinn p
hafi verið búin til með
p = Path("mappa/mappa/...")
|
algild slóð fyrir p |
|
yfirmappa p |
|
aftasti hluti p, skráin eða mappan sem p lýsir |
|
undirnafn skrár (t.d. |
|
aðalnafn skrár (nafn án undirnafns) |
|
slóð núverandi möppu (current working directory) |
|
slóð heimamöppu |
|
satt ef slóðin p er til |
|
satt ef p er mappa (directory) |
|
satt ef p er skrá |
|
eyðir skrá með slóð p |
|
eyðir möppu með slóð p (remove) |
|
býr til möppu með slóð p (make) |
|
ítrari fyrir allar skrár og undirmöppur í p |
|
slóð fyrir möppu undir p |
|
slóð fyrir skrá undir p |
Takið eftir að sumar aðgerðirnar eru ekki með () á eftir: Þær eru það sem kallað
er „eiginleikar“ en ekki aðferðir. Aðferðirnar p.cwd()
og p.home()
eru
reyndar þannig að það skiptir engu máli hvaða slóð var notuð til að búa til p.
Sýnidæmi: Notkun Pathlib
Hér t.h. er hluti af möppukerfi Toms. Ef notandi er staddur í möppunni Tools
þá mundi eftirfarandi forritsbútur ítra sig yfir innihald hennar og skrifa út
Format, Stats, Old
. Að því loknu skrifast True, Notes
(aðalnafn
Notes.txt):
from pathlib import Path
mappa = Path(".")
for m in mappa.iterdir():
print(m.name(), end=", ")
print()
nótur = Path("../Notes.txt")
print(nótur.exists(), nótur.stem())
Æfing: Ítrað yfir möppu
Reiknað er með að æfingarnar í köflum 8.2.3 og 8.4 hafi verið leystar og því séu nokkrar skrár í núverandi möppu (data.txt, xy.dat, xy1.dat).
Finnið út algilda slóð núverandi möppu með því að nota Path.
Skrifið forritsbút sem ítrar yfir innihald þessarar möppu og ákvarðar fyrir hvern hlut sem finnst hvort hann sé skrá eða mappa.
Búið til nýja möppu „prufa“ og skrifið svo skrá þar, „tilraun.txt“ með nafninu ykkar. Finnið hana í vinstri spássíunni og skoðið [Hér má nota neðstu skipunina í töflu 8.1 og svo er hægt að nota Path-hluti sem viðföng í open-fallið].