io — ulazno/izlazni tokovi

Ovaj modul sadrži dodatne tipove objekata stream (sličnih datotekama) te pomoćne funkcije. Izlaže ugrađenu funkciju open() zajedno s tekstualnim i binarnim međuspremnicima u memoriji (StringIO, BytesIO) koji implementiraju standardno sučelje tokova read/write/seek.

Konceptualna hijerarhija

Razlika u odnosu na CPython

Konceptualna hijerarhija osnovnih klasa tokova pojednostavljena je u MicroPythonu, kako je opisano u ovom odjeljku.

(Apstraktne) osnovne klase tokova, koje služe kao temelj za ponašanje svih konkretnih klasa, u CPythonu se pridržavaju nekoliko dihotomija (razvrstavanja u parove). U MicroPythonu su one donekle pojednostavljene i učinjene implicitnima radi postizanja veće učinkovitosti i uštede resursa.

Važna dihotomija u CPythonu jest razlika između tokova bez međuspremnika i tokova s međuspremnikom. U MicroPythonu su trenutačno svi tokovi bez međuspremnika. To je zato što svi moderni operativni sustavi, pa čak i mnogi RTOS-ovi i upravljački programi datotečnih sustava, već obavljaju međupohranu na svojoj strani. Dodavanje još jednog sloja međupohrane kontraproduktivno je (problem poznat kao „bufferbloat”) i troši dragocjenu memoriju. Imajte na umu da i dalje postoje slučajevi u kojima međupohrana može biti korisna, pa bismo naknadno mogli uvesti opcionalnu podršku za međupohranu.

Ali u CPythonu je još jedna važna dihotomija vezana uz „međupohranjenost” - radi se o tome može li tok dovesti do kratkih čitanja/pisanja ili ne. Kratko čitanje je kada korisnik zatraži npr. 10 bajtova iz toka, ali dobije manje; slično vrijedi za pisanja. U CPythonu su tokovi bez međuspremnika automatski podložni kratkim operacijama, dok tokovi s međuspremnikom jamče da do njih neće doći. Odsutnost kratkih čitanja/pisanja važna je značajka jer omogućuje razvoj sažetijih i učinkovitijih programa - što je vrlo poželjno za MicroPython. Dakle, iako MicroPython ne podržava tokove s međuspremnikom, ipak omogućuje tokove bez kratkih operacija. Hoće li doći do kratkih operacija ili ne ovisi o potrebama svake pojedine klase, no programerima se snažno savjetuje da iz gore navedenih razloga daju prednost ponašanju bez kratkih operacija. Na primjer, za MicroPython sockete jamči se da će izbjegavati kratka čitanja/pisanja. Zapravo, trenutačno u jezgri nema primjera klase toka s kratkim operacijama, a takva bi klasa bila specifična za određeni hardver.

Ponašanje bez kratkih operacija postaje zamršeno u slučaju neblokirajućih tokova, pri čemu je razlika između blokirajućeg i neblokirajućeg ponašanja još jedna CPython dihotomija koju MicroPython u potpunosti podržava. Neblokirajući tokovi nikada ne čekaju da podaci stignu ili budu zapisani - čitaju/pišu što god je moguće ili signaliziraju nedostatak podataka (ili mogućnosti pisanja podataka). Očito je da je to u sukobu s pravilom „bez kratkih operacija”, i doista, slučaj neblokirajućih tokova s međuspremnikom (a time i bez kratkih operacija) zamršen je u CPythonu - na nekim mjestima takva je kombinacija zabranjena, na nekima je nedefinirana ili jednostavno nedokumentirana, a u nekim slučajevima podiže opširne iznimke. Stvar je mnogo jednostavnija u MicroPythonu: neblokirajući tokovi važni su za učinkovite asinkrone operacije, pa ovo svojstvo prevladava nad onim „bez kratkih operacija”. Dakle, iako će blokirajući tokovi izbjegavati kratka čitanja/pisanja kad god je to moguće (jedini slučaj kratkog čitanja jest kada se dosegne kraj datoteke ili u slučaju pogreške (no pogreške ne vraćaju kratke podatke, već podižu iznimke)), neblokirajući tokovi mogu proizvesti kratke podatke kako bi izbjegli blokiranje operacije.

Posljednja dihotomija je razlika između binarnih i tekstualnih tokova. MicroPython ih, naravno, podržava, ali dok su u CPythonu tekstualni tokovi inherentno s međuspremnikom, u MicroPythonu to nisu. (Doista, to je jedan od slučajeva za koje bismo mogli uvesti podršku za međupohranu.)

Imajte na umu da MicroPython radi učinkovitosti ne pruža apstraktne osnovne klase koje odgovaraju gornjoj hijerarhiji, te nije moguće implementirati ili izvesti potklasu klase toka u čistom Pythonu.

Funkcije

io.open(name: str, mode: str = 'r', **kwargs) Any

Otvara datoteku. Ugrađena funkcija open() predstavlja alias za ovu funkciju. Parametar mode uvijek je podržan; podrška za ostale argumente može varirati.

Klase

class io.IOBase

Osnovna klasa za objekte tokova („sličnih datotekama”). Konkretne potklase implementiraju niskorazinske I/O metode navedene u nastavku (readinto, write, ioctl); izvršno okruženje na njima gradi viši protokol tokova (read, readline, readlines, close, iteracija), pa svaka instanca toka podržava te metode čak i kada ih potklasa ne definira.

Implementacijske metode (nadjačajte ih u potklasi):

readinto(buf: bytearray) int | None

Čita bajtove u zapisivi međuspremnik buf. Vraća broj pročitanih bajtova, 0 na kraju toka ili None ako trenutačno nema dostupnih podataka (za neblokirajući tok).

write(buf: bytes) int | None

Zapisuje bajtove iz buf. Vraća broj zapisanih bajtova ili None ako se zapisivanje trenutačno ne može izvršiti (za neblokirajući tok).

ioctl(request: int, arg: int) int

Upravlja temeljnim tokom/uređajem. request je jedan od MP_STREAM_* kodova zahtjeva. Vraća nenegativnu vrijednost u slučaju uspjeha ili negativnu errno vrijednost u slučaju pogreške.

Metode protokola tokova (dostupne na svakoj instanci toka):

read(size: int = -1)

Čita i vraća najviše size bajtova (ili znakova, u tekstualnom načinu). Ako je size izostavljen ili negativan, čita do kraja toka. Vraća bytes za binarne tokove i str za tekstualne tokove; prazan rezultat označava kraj toka.

readline(size: int = -1)

Čita i vraća jedan redak, uključujući završni znak novog retka ako je prisutan. Ako je zadan size, čita se najviše size bajtova (ili znakova). Na kraju toka vraća prazan bytes / str.

readlines() list

Čita do kraja toka i vraća list redaka, svaki sa svojim završnim znakom novog retka.

close() None

Zatvara tok i oslobađa sve temeljne resurse. Operacije nad zatvorenim tokom podižu OSError (ili ValueError za tokove u memoriji).

seek(offset: int, whence: int = 0) int

Mijenja trenutačni položaj u toku na offset bajtova relativno na whence (0 = početak toka, 1 = trenutačni položaj, 2 = kraj toka). Vraća novi apsolutni položaj. Podiže OSError na toku po kojem se ne može pozicionirati.

tell() int

Vraća trenutačni apsolutni položaj u toku. Ekvivalentno seek(0, 1).

flush() None

Prazni sve međuspremnike za pisanje, prosljeđujući podatke koji čekaju temeljnom uređaju ili datoteci. Bez učinka na tokovima koji ne koriste međuspremnik.

Izravna iteracija toka pri svakom prolazu daje jedan redak – ekvivalentno pozivanju readline() u petlji dok se ne vrati graničnik praznog retka koji označava kraj toka. Tok također podržava protokol upravitelja konteksta, pa with open(...) as f: automatski zatvara tok.

Napomena

MicroPythonov modul za tokove izlaže i C pomoćnike s nastavkom „1” mp_stream_read1_obj, mp_stream_readinto1_obj i mp_stream_write1_obj koji obavljaju jedan temeljni I/O poziv umjesto petlje sve dok zahtjev nije potpuno ispunjen. Njih interno koriste klase poput machine.UART za implementaciju vlastitog read / write – ali nijedna standardna klasa toka ne veže ih kao metode read1 / readinto1 / write1 pozivne iz Pythona.

class io.StringIO(string: str = '')

Objekt u memoriji sličan datoteci za ulaz/izlaz u tekstualnom načinu (sličan običnoj datoteci otvorenoj s modifikatorom „t”). Početni sadržaj može se zadati parametrom string (koji bi trebao biti običan string). Instance također podržavaju protokol upravitelja konteksta (upotrebljiv u izjavi with).

read(size: int = -1) str

Čita i vraća najviše size znakova. Ako je size izostavljen ili negativan, čita i vraća sav preostali sadržaj.

readline(size: int = -1) str

Čita i vraća jedan redak. Ako je zadan size, čita se najviše size znakova.

readinto(buf: bytearray) int

Čita u unaprijed alocirani, zapisivi međuspremnik buf i vraća broj pročitanih bajtova.

write(s: str) int

Zapisuje string s i vraća broj zapisanih znakova.

seek(offset: int, whence: int = 0) int

Mijenja položaj u toku na offset relativno na whence (0 = početak, 1 = trenutačni, 2 = kraj) i vraća novi apsolutni položaj.

tell() int

Vraća trenutačni položaj u toku.

flush() None

Prazni međuspremnike za pisanje. Ovo nema učinka za tok u memoriji.

close() None

Zatvara tok i oslobađa temeljni međuspremnik. Daljnje operacije nad zatvorenim tokom podižu ValueError.

getvalue() str

Vraća trenutačni sadržaj temeljnog međuspremnika.

class io.StringIO(alloc_size: int)

Stvara prazan StringIO objekt unaprijed alociran za pohranu do alloc_size bajtova, tako da zapisivanje do toliko bajtova neće ponovno alocirati međuspremnik (izbjegavajući stanje nedostatka memorije ili fragmentaciju memorije). Ovaj je konstruktor MicroPython proširenje preporučeno samo za posebne slučajeve i biblioteke na razini sustava, a ne za aplikacije krajnjih korisnika.

Razlika u odnosu na CPython

Ovaj je konstruktor MicroPython proširenje.

read(size: int = -1) str

Čita i vraća najviše size znakova. Ako je size izostavljen ili negativan, čita i vraća sav preostali sadržaj.

readline(size: int = -1) str

Čita i vraća jedan redak. Ako je zadan size, čita se najviše size znakova.

readinto(buf: bytearray) int

Čita u unaprijed alocirani, zapisivi međuspremnik buf i vraća broj pročitanih bajtova.

write(s: str) int

Zapisuje string s i vraća broj zapisanih znakova.

seek(offset: int, whence: int = 0) int

Mijenja položaj u toku na offset relativno na whence (0 = početak, 1 = trenutačni, 2 = kraj) i vraća novi apsolutni položaj.

tell() int

Vraća trenutačni položaj u toku.

flush() None

Prazni međuspremnike za pisanje. Ovo nema učinka za tok u memoriji.

close() None

Zatvara tok i oslobađa temeljni međuspremnik. Daljnje operacije nad zatvorenim tokom podižu ValueError.

getvalue() str

Vraća trenutačni sadržaj temeljnog međuspremnika.

class io.BytesIO(string: bytes = b'')

Objekt u memoriji sličan datoteci za ulaz/izlaz u binarnom načinu (sličan običnoj datoteci otvorenoj s modifikatorom „b”). Početni sadržaj može se zadati parametrom string (koji bi trebao biti bytes objekt). Instance također podržavaju protokol upravitelja konteksta (upotrebljiv u izjavi with).

read(size: int = -1) bytes

Čita i vraća najviše size bajtova. Ako je size izostavljen ili negativan, čita i vraća sav preostali sadržaj.

readline(size: int = -1) bytes

Čita i vraća jedan redak. Ako je zadan size, čita se najviše size bajtova.

readinto(buf: bytearray) int

Čita u unaprijed alocirani, zapisivi međuspremnik buf i vraća broj pročitanih bajtova.

write(b: bytes) int

Zapisuje objekt sličan bajtovima b i vraća broj zapisanih bajtova.

seek(offset: int, whence: int = 0) int

Mijenja položaj u toku na offset relativno na whence (0 = početak, 1 = trenutačni, 2 = kraj) i vraća novi apsolutni položaj.

tell() int

Vraća trenutačni položaj u toku.

flush() None

Prazni međuspremnike za pisanje. Ovo nema učinka za tok u memoriji.

close() None

Zatvara tok i oslobađa temeljni međuspremnik. Daljnje operacije nad zatvorenim tokom podižu ValueError.

getvalue() bytes

Vraća trenutačni sadržaj temeljnog međuspremnika.

class io.BytesIO(alloc_size: int)

Stvara prazan BytesIO objekt unaprijed alociran za pohranu do alloc_size bajtova, tako da zapisivanje do toliko bajtova neće ponovno alocirati međuspremnik (izbjegavajući stanje nedostatka memorije ili fragmentaciju memorije). Ovaj je konstruktor MicroPython proširenje preporučeno samo za posebne slučajeve i biblioteke na razini sustava, a ne za aplikacije krajnjih korisnika.

Razlika u odnosu na CPython

Ovaj je konstruktor MicroPython proširenje.

read(size: int = -1) bytes

Čita i vraća najviše size bajtova. Ako je size izostavljen ili negativan, čita i vraća sav preostali sadržaj.

readline(size: int = -1) bytes

Čita i vraća jedan redak. Ako je zadan size, čita se najviše size bajtova.

readinto(buf: bytearray) int

Čita u unaprijed alocirani, zapisivi međuspremnik buf i vraća broj pročitanih bajtova.

write(b: bytes) int

Zapisuje objekt sličan bajtovima b i vraća broj zapisanih bajtova.

seek(offset: int, whence: int = 0) int

Mijenja položaj u toku na offset relativno na whence (0 = početak, 1 = trenutačni, 2 = kraj) i vraća novi apsolutni položaj.

tell() int

Vraća trenutačni položaj u toku.

flush() None

Prazni međuspremnike za pisanje. Ovo nema učinka za tok u memoriji.

close() None

Zatvara tok i oslobađa temeljni međuspremnik. Daljnje operacije nad zatvorenim tokom podižu ValueError.

getvalue() bytes

Vraća trenutačni sadržaj temeljnog međuspremnika.