Práce s řetězci a se soubory

Podívejme se v rychlosti, jak Python pracuje s řetězci a se soubory. Ukážeme si základní principy a jednoduché příklady.

Řetězce -- Python str

S řetězci jsme se už setkali mnohokrát, řekli jsme si také, že str objekt je immutable (neměnitelný). V rychlosti teď shrneme základy.

In [1]:
print("řetězce jsou ve dvojitých")
řetězce jsou ve dvojitých
In [2]:
print('nebo jednoduchých uvozovkách, tj. " nebo \'')
nebo jednoduchých uvozovkách, tj. " nebo '
In [3]:
print('řetězce spojíme ' + 'operátorem +')
řetězce spojíme operátorem +
In [4]:
print('+ můžeme případně vynechat, '
      'takže dlouhé řetězce můžeme rozložit'
      'do více řádků, nejlépe uvnitř závorek')
+ můžeme případně vynechat, takže dlouhé řetězce můžeme rozložitdo více řádků, nejlépe uvnitř závorek

Python podporuje unicode:

In [5]:
print("Τὴ γλῶσσα μοῦ ἔδωσαν ἑλληνικὴ")
Τὴ γλῶσσα μοῦ ἔδωσαν ἑλληνικὴ
In [6]:
# pokud chceme psát spoustu speciálních znaků, např. \, použijeme r" ..."
# to se hodí třeba pro LaTeX
print(r"\[\frac{{\partial \psi }}{{\partial R}}\]")
\[\frac{{\partial \psi }}{{\partial R}}\]
In [7]:
s = "řřeettěězzccee  ppooddppoorruujjíí  řřeezzyy"
print(s[::2])
řetězce podporují řezy
In [8]:
s = "řetězce lze " + 3 * "násobit "
print(s)
řetězce lze násobit násobit násobit 

f-strings

Python 3.6 zavedl moderní způsob formátování řetězců pomoci tzv. f-strings. Syntaxe je velice jednoduchá: před první uvozovky vložit znak f a pak všechny výrazy uvnitř {složených závorek} nahradit jejich textovou reprezentací.

Např.:

In [9]:
name = "Eric"
age = 74
f"Hello, {name}. You are {age}."
Out[9]:
'Hello, Eric. You are 74.'
In [10]:
f"2 * 37 = {2 * 37}"
Out[10]:
'2 * 37 = 74'

Můžeme volat i metody / funce:

In [11]:
name = "Eric Idle"
f"{name.lower()} is funny."
Out[11]:
'eric idle is funny.'

Výrazy se dají formátovat pomocí formátovacího mini-jazyka:

In [12]:
import decimal

value = decimal.Decimal("12.34567")
width = 10
precision = 4

f"result: {value:{width}.{precision}}"
Out[12]:
'result:      12.35'
In [13]:
import datetime as dt

today = dt.date.today()
f"Taday is {today:%B %d, %Y}"
Out[13]:
'Taday is November 05, 2019'

Existují ještě dva starší (zastaralé) způsoby formátování: pomocí % operátoru a pomocí format metody. Doporučení je používat už jen f-strings, případně string.Template. Viz např. https://realpython.com/python-string-formatting/#which-string-formatting-method-should-you-use.

python string formatting flowchart

Metody třídy str

Výpis "veřejných" metod str, k němuž použijeme join pro vytvoření řetězce z iterátoru a startswith pro test začátku řetězce.

In [14]:
", ".join([m for m in dir("") if not m.startswith("_")])
Out[14]:
'capitalize, casefold, center, count, encode, endswith, expandtabs, find, format, format_map, index, isalnum, isalpha, isascii, isdecimal, isdigit, isidentifier, islower, isnumeric, isprintable, isspace, istitle, isupper, join, ljust, lower, lstrip, maketrans, partition, replace, rfind, rindex, rjust, rpartition, rsplit, rstrip, split, splitlines, startswith, strip, swapcase, title, translate, upper, zfill'

Mezery apod. ořízneme pomocí strip.

In [15]:
s = "  \t abc\n\n"
print(s)
print(s.strip())
  	 abc


abc

Často se hodí split, je to vlastně opak join.

In [16]:
s = "1, 2, 3, čtyři, 5"
# rozdílema na částí oddělené čárkou
s = s.split(",")
print(s)
# zkusíme převést na čísla
s = [int(a) for a in s if a.strip().isdigit()]
print(s)
['1', ' 2', ' 3', ' čtyři', ' 5']
[1, 2, 3, 5]

Velikost písmen mění upper, lower, capitalize, swapcase

In [17]:
print("všechna písmena velká".upper())
VŠECHNA PÍSMENA VELKÁ

Základy práce se soubory

Pro práci se sounory je základní příkaz open, který vrací instanci file

In [18]:
f = open("./150_prace-s-retezci-a-se-soubory.ipynb", "r")
print(f)
<_io.TextIOWrapper name='./150_prace-s-retezci-a-se-soubory.ipynb' mode='r' encoding='UTF-8'>
In [19]:
# metody file
", ".join([m for m in dir(f) if not m.startswith("_")])
Out[19]:
'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'
In [20]:
# teď soubor zavřeme
f.close()

Nejčastější je procházet soubor jako iterátor.

In [21]:
f = open("./150_prace-s-retezci-a-se-soubory.ipynb", "r")

# print first 10 lines with line numbers and max 20 characters per line
for count, line in enumerate(f):
    print(f"{count}: {line[:20].rstrip()}")
    if count == 10:
        break
f.close()
0: {
1:  "cells": [
2:   {
3:    "cell_type": "mar
4:    "metadata": {},
5:    "source": [
6:     "Podívejme se v
7:     "<!-- TEASER_END
8:    ]
9:   },
10:   {

Pro práci se soubory je velice užitečný (a jednoznačně preferevaný) blok with, který používá tzv. context managery. To nám zajistí, že soubor bude vždy zavřen, i když během práce se souborem dojde k chybě (neodchycená výjimka). Nahrazuje to tak try..except..finally blok.

Použití je velice jednoduché, předchozí příklad by vypadal takto:

In [22]:
with open("./150_prace-s-retezci-a-se-soubory.ipynb", "r") as f:
    # print first 10 lines with line numbers and max 20 characters per line
    for count, line in enumerate(f):
        print(f"{count}: {line[:20].rstrip()}")
        if count == 10:
            break
0: {
1:  "cells": [
2:   {
3:    "cell_type": "mar
4:    "metadata": {},
5:    "source": [
6:     "Podívejme se v
7:     "<!-- TEASER_END
8:    ]
9:   },
10:   {

Všimněte si, že chybí explicitní volání f.close().

Komentáře

Comments powered by Disqus