From fd79b21ce041babd0fc2f25ae1731405ff93ba5e Mon Sep 17 00:00:00 2001 From: Martin Mares <mj@ucw.cz> Date: Tue, 17 Dec 2019 00:18:13 +0100 Subject: [PATCH] =?UTF-8?q?Soubory=20a=20v=C3=BDjimky?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- 11-soubory/11-soubory.tex | 276 ++++++++++++++++++++++++++++++++++++++ 11-soubory/Makefile | 3 + 11-soubory/exception.py | 8 ++ 11-soubory/file-triv.py | 3 + 11-soubory/file-with.py | 2 + 11-soubory/test.err | 6 + 11-soubory/test.py | 4 + 7 files changed, 302 insertions(+) create mode 100644 11-soubory/11-soubory.tex create mode 100644 11-soubory/Makefile create mode 100644 11-soubory/exception.py create mode 100644 11-soubory/file-triv.py create mode 100644 11-soubory/file-with.py create mode 100644 11-soubory/test.err create mode 100644 11-soubory/test.py diff --git a/11-soubory/11-soubory.tex b/11-soubory/11-soubory.tex new file mode 100644 index 0000000..5efb5a9 --- /dev/null +++ b/11-soubory/11-soubory.tex @@ -0,0 +1,276 @@ +\documentclass{beamer} +\usepackage[utf8]{inputenc} +\usepackage[czech]{babel} +\usepackage{palatino} +\usepackage{verbatim} +\usetheme{Warsaw} +\title{Programování 1: Soubory a výjimky} +\author[Martin Mareš]{Martin Mareš\\\texttt{mj@ucw.cz}} +\institute{Katedra Aplikované Matematiky\\MFF UK Praha} +\date{2019} +\begin{document} +\setbeamertemplate{navigation symbols}{} +\setbeamertemplate{footline}{} +\setbeamerfont{title page}{family=\rmfamily} +\shorthandoff{"} + +\begin{frame} +\titlepage +\end{frame} + +\input ../slidemac.tex + +% ---------------------------------------------------------------------- + +\begin{frame}{Soubory} + +Soubor je pojmenovaná posloupnost {\bf bajtů} (8-bitových hodnot). + +~ + +Nás budou zajímat hlavně {\bf textové soubory:} + +\begin{itemize} + +\item Skládají se ze {\bf znaků} převedených na bajty nějakým {\bf kódováním}, +nejčastěji: + + \begin{itemize} + \item ASCII (\uv{\kern1pt anglická abeceda} o~95 znacích) + \item iso-8859-2 (navíc znaky východoevropských jazyků) + \item cp1250 (něco podobného specifického pro Windows) + \item UTF-8 (vícebajtové znaky, pokrývá většinu jazyků světa) + \end{itemize} + +\item Soubor je členěn na řádky, každý končí speciálním {\bf znakem konce řádku} +(pozor, různé operační systémy ukončují řádky různě, ale Python to překládá). + +\end{itemize} + +\end{frame} + +% ---------------------------------------------------------------------- + +\begin{frame}{Jednoduchý příklad} + +\verbatiminput{file-triv.py} + +{\bf open} otevírá soubor, dostává: + +\begin{itemize} +\item jméno souboru +\item mód přístupu: + \begin{itemize} + \item {\tt r} = čtení + \item {\tt w} = zápis (založí/vyprázdní soubor) + \item {\tt a} = zápis na konec (append) + \item {\tt r+/w+} = čtení i zápis + \item {\tt rb} = binární čtení (bajty, ne text) + \end{itemize} +\item {\tt encoding=}kódování (default: podle OS) +\end{itemize} + +\bigskip + +Explicitnimu {\bf close} se můžeme vyhnout takto: + +\verbatiminput{file-with.py} + +\end{frame} + +% ---------------------------------------------------------------------- + +\begin{frame}{Co můžeme dělat se souborem} + +Metody souborů: + +\begin{itemize} + +\item {\tt f.write(text)} -- zapíše text + +\item {\tt f.read(n)} -- přečte dalších $n$ znaků ({\tt ""} na konci) + +\item {\tt f.read()} -- přečte všechny zbývající znaky + +\item {\tt f.readline()} -- přečte další řádek (včetně {\tt {\char92}n}) nebo {\tt ""} + +\item {\tt f.seek(...)} -- přesune se na danou pozici v~souboru + +\end{itemize} + +\bigskip + +Další operace: + +\begin{itemize} + +\item {\tt print(..., file=f)} + +\item {\tt for line in f:} -- cyklus přes řádky souboru + +\end{itemize} + +\bigskip + +Pozor, řádky končí na {\tt "{\char92}n"}, hodí se zavolat {\tt rstrip()}. + +\end{frame} + +% ---------------------------------------------------------------------- + +\begin{frame}{Standardní vstup a výstup} + +Vždy je k~dispozici: + +\medskip + +\begin{itemize} + +\item {\tt sys.stdin} -- standardní vstup (odtud čte {\tt input()}) + +\item {\tt sys.stdout} -- standardní výstup (sem píše {\tt print()}) + +\item {\tt sys.stderr} -- standardní chybový výstup + +\end{itemize} + +\end{frame} + +% ---------------------------------------------------------------------- + +\begin{frame}{Formátování} + +\py{% +"\{\} leží \{\}".format("kočka", "na okně") +}{% +'kočka leží na okně' +} + +\py{% +"\{1\} leží \{0\}".format("kočka", "na okně") +}{% +'na okně leží kočka' +} + +\py{% +"\{kdo\} leží \{kde\}".format(kdo="pes", kde="v boudě") +}{% +'pes leží v boudě' +} + +\py{% +kdo="lenochod"\\ +kde="na větvi"\\ +f"\{kdo\} leží \{kde\}" +}{% +'lenochod leží na větvi' +} + +\py{% +"\{0:05\} < \{1:05\}".format(1, 2) +}{% +'00001 < 00002' \cmt{(další varianty viz dříve)} +} + +\end{frame} + +% ---------------------------------------------------------------------- + +\begin{frame}{Hlášení chyb} + +{\bf test.py:} + +\verbatiminput{test.py} + +\medskip + +{\bf Po spuštění dostaneme:} + +\verbatiminput{test.err} + +\end{frame} + +% ---------------------------------------------------------------------- + +\begin{frame}{Výjimky} + +Chyba vygeneruje {\bf výjimku}, například těchto typů: + +\medskip + +\begin{itemize} + +\item ZeroDivisionError -- dělení nulou + +\item ValueError -- chybný argument (třeba {\tt log(-4)}) + +\item IndexError -- přístup k~indexu mimo rozsah + +\item KeyError -- čtení neexistujícího klíče ve slovníku + +\item FileNotFoundError -- otevření neexistujícího souboru + +\item MemoryError -- došla paměť + +\item KeyboardInterrupt -- běh programu přerušen pomocí Ctrl-C + +\end{itemize} + +\end{frame} + +% ---------------------------------------------------------------------- + +\begin{frame}{Odchycení výjimky} + +\verbatiminput{exception.py} + +\medskip + +Výjimky jsou objekty, jejich typy jsou třídy. + +\medskip + +Výjimka se umí převést na řetězec ({\tt print} ji vypíše). + +\medskip + +Výjimka má atributy (detaily toho, co se stalo a kde). + +\medskip + +Typy výjimek tvoří hierarchii (třeba {\tt FileNotFoundError} je potomkem {\tt OSError}), +{\tt except} umí zachytit i obecnější typ. + +\end{frame} + +% ---------------------------------------------------------------------- + +\begin{frame}{Vyvolání výjimky} + +\py{% +raise RuntimeError("Jejda!") +}{% +Traceback (most recent call last):\\ +~~File "<stdin>", line 1, in <module>\\ +RuntimeError: Jejda! +} + +\py{% +assert 1 == 2 +}{% +[...]\\ +AssertionError +} + +\py{% +assert 1 == 2, "Svět se nezbláznil" +}{% +[...]\\ +AssertionError: Svět se nezbláznil +} + +\end{frame} + +% ---------------------------------------------------------------------- + +\end{document} diff --git a/11-soubory/Makefile b/11-soubory/Makefile new file mode 100644 index 0000000..6aaef9d --- /dev/null +++ b/11-soubory/Makefile @@ -0,0 +1,3 @@ +SLIDES=11-soubory.pdf + +include ../Makerules diff --git a/11-soubory/exception.py b/11-soubory/exception.py new file mode 100644 index 0000000..8483f86 --- /dev/null +++ b/11-soubory/exception.py @@ -0,0 +1,8 @@ +try: + x, y = map(int, input().split()) + print(x/y) +except ZeroDivisionError: + print("Nulou dělit neumím.") +except ValueError as x: + print("Chyba:", x) + print("Zadejte prosím dvě čísla.") diff --git a/11-soubory/file-triv.py b/11-soubory/file-triv.py new file mode 100644 index 0000000..4602ac8 --- /dev/null +++ b/11-soubory/file-triv.py @@ -0,0 +1,3 @@ +f = open('soubor.txt', 'w') +f.write('Hej mistře!\n') +f.close() diff --git a/11-soubory/file-with.py b/11-soubory/file-with.py new file mode 100644 index 0000000..d55bb66 --- /dev/null +++ b/11-soubory/file-with.py @@ -0,0 +1,2 @@ +with open('soubor.txt', 'w') as f: + f.write('Hej mistře!\n') diff --git a/11-soubory/test.err b/11-soubory/test.err new file mode 100644 index 0000000..5a4c61a --- /dev/null +++ b/11-soubory/test.err @@ -0,0 +1,6 @@ +Traceback (most recent call last): + File "test.py", line 4, in <module> + f(1, 0) + File "test.py", line 2, in f + print(x/y) +ZeroDivisionError: division by zero diff --git a/11-soubory/test.py b/11-soubory/test.py new file mode 100644 index 0000000..e8f45eb --- /dev/null +++ b/11-soubory/test.py @@ -0,0 +1,4 @@ +def f(x, y): + print(x/y) + +f(1, 0) -- GitLab