Szczegóły ebooka

Python. Szybko i prosto. Wydanie III

Python. Szybko i prosto. Wydanie III

Naomi Ceder

Ebook

Na początku, w 1989 roku, był tylko wakacyjnym projektem Guida van Rossuma. Dziś jest potężnym językiem programowania o niesamowitej wszechstronności: można się nim posłużyć do napisania skryptu ułatwiającego prace administratora sieci, stworzenia aplikacji internetowej, a także opracowania systemu głębokiego uczenia maszynowego. Co więcej, dookoła Pythona skupiła się międzynarodowa społeczność tworząca niesamowite biblioteki i frameworki, co przenosi programowanie w Pythonie na zupełnie inny poziom. Ten język ma i taką ważną zaletę, że jego nauka jest przyjemna i angażująca. Nawet początkujący programista może bardzo szybko zacząć pisać poprawny i dobrze działający kod.

Dzięki tej książce zaczniesz błyskawicznie programować w Pythonie! Pominięto tu zbędne szczegóły, a skoncentrowano się na najważniejszych dla programisty, fundamentalnych zasadach programowania: przepływie sterowania, programowaniu zorientowanym obiektowo, dostępie do plików czy obsłudze wyjątków. Liczne porady, wskazówki i obszerne przykłady pomogą Ci w opanowaniu poszczególnych zagadnień. Poza omówieniem Pythona, jego najważniejszych bibliotek, pakietów i narzędzi w tym wydaniu znajdziesz pięć nowych rozdziałów dotyczących data science. Praca z tym podręcznikiem sprawi, że szybko będziesz gotów nawet na bardzo trudne zadania - i w pełni wykorzystasz potencjał Pythona!

W tej książce między innymi:

  • wprowadzenie do Pythona i przygotowanie IDLE - środowiska pracy
  • tworzenie kodu niezależnego od platformy
  • dostęp do relacyjnych i nierelacyjnych baz danych
  • obsługa wyjątków i praca na plikach
  • pakiety w Pythonie

Python: język elegancki, wszechstronny, elastyczny!

 

O autorce 15

 

Przedmowa 17

Wprowadzenie 19

Podziękowania 21

O książce 23

CZĘŚĆ I. ZACZYNAMY 27

Rozdział 1. O Pythonie 29

  • 1.1. Czemu powinienem uczyć się właśnie Pythona? 29
  • 1.2. W czym Python wypada dobrze? 30
    • 1.2.1. Python jest łatwy w użyciu 30
    • 1.2.2. Python jest zwięzły 30
    • 1.2.3. Python jest czytelny 31
    • 1.2.4. Python jest kompletny 32
    • 1.2.5. Python jest wieloplatformowy 32
    • 1.2.6. Python jest darmowy 32
  • 1.3. Z czym Python sobie nie radzi? 33
    • 1.3.1. Python nie jest najszybszym z języków 33
    • 1.3.2. Python nie ma największej liczby bibliotek 34
    • 1.3.3. Python nie sprawdza typów zmiennych podczas kompilacji 34
    • 1.3.4. Python słabo wspiera urządzenia mobilne 34
    • 1.3.5. Python nie wykorzystuje dobrze wielu procesorów naraz 34
  • 1.4. Po co uczyć się Pythona 3? 35
  • Podsumowanie 36

Rozdział 2. Pierwsze kroki 37

  • 2.1. Instalacja Pythona 37
  • 2.2. Podstawy trybu interaktywnego i IDLE 39
    • 2.2.1. Podstawowy tryb konsolowy 39
    • 2.2.2. Zintegrowane środowisko programistyczne IDLE 40
    • 2.2.3. Wybór pomiędzy podstawowym trybem konsolowym a IDLE 41
  • 2.3. Używanie okna konsoli Pythona w IDLE 41
  • 2.4. Witaj, świecie 42
  • 2.5. Używanie konsoli do poznania możliwości Pythona 42
  • Podsumowanie 44

Rozdział 3. Przegląd najważniejszych zagadnień w Pythonie 45

  • 3.1. Python w skrócie 46
  • 3.2. Typy wbudowane 46
    • 3.2.1. Liczby 46
    • 3.2.2. Listy 48
    • 3.2.3. Krotki 49
    • 3.2.4. Łańcuchy znaków 50
    • 3.2.5. Słowniki 51
    • 3.2.6. Zbiory 52
    • 3.2.7. Obiekty plików 52
  • 3.3. Kontrola przepływu sterowania 53
    • 3.3.1. Wartości logiczne i wyrażenia 53
    • 3.3.2. Instrukcja if-elif-else 53
    • 3.3.3. Pętla while 54
    • 3.3.4. Pętla for 54
    • 3.3.5. Definiowanie funkcji 55
    • 3.3.6. Wyjątki 55
    • 3.3.7. Kontekstowa obsługa błędów i słowo kluczowe with 56
  • 3.4. Tworzenie modułów 57
  • 3.5. Programowanie zorientowane obiektowo 58
  • Podsumowanie 59

CZĘŚĆ II. PODSTAWY 61

Rozdział 4. Podstawy podstaw 63

  • 4.1. Struktura wcięć i bloków 63
  • 4.2. Zróżnicowanie komentarzy 65
  • 4.3. Zmienne i przypisania 65
  • 4.4. Wyrażenia 67
  • 4.5. Łańcuchy znaków 68
  • 4.6. Liczby 68
    • 4.6.1. Wbudowane funkcje liczbowe 70
    • 4.6.2. Zaawansowane funkcje liczbowe 70
    • 4.6.3. Przeliczenia liczbowe 70
    • 4.6.4. Liczby zespolone 70
    • 4.6.5. Zaawansowane funkcje na liczbach zespolonych 71
  • 4.7. Wartość None 72
  • 4.8. Uzyskiwanie danych od użytkownika 72
  • 4.9. Wbudowane operatory 73
  • 4.10. Podstawy stylu typowego dla Pythona 73
  • Podsumowanie 73

Rozdział 5. Listy, krotki i zbiory 75

  • 5.1. Listy a tablice 76
  • 5.2. Indeksy list 76
  • 5.3. Modyfikowanie list 78
  • 5.4. Sortowanie list 80
    • 5.4.1. Własne mechanizmy sortowania 81
    • 5.4.2. Funkcja sorted 83
  • 5.5. Inne przydatne działania na listach 83
    • 5.5.1. Przynależność do zbioru i operator in 83
    • 5.5.2. Konkatenacja list i operator + 83
    • 5.5.3. Inicjalizacja listy i operator * 83
    • 5.5.4. Maksymalna i minimalna wartość elementu oraz funkcje max i min 84
    • 5.5.5. Przeszukiwanie listy i metoda index 84
    • 5.5.6. Wystąpienia elementu i metoda count 85
    • 5.5.7. Podsumowanie działań na listach 85
  • 5.6. Listy zagnieżdżone i kopie głębokie 86
  • 5.7. Krotki 88
    • 5.7.1. Podstawy krotek 88
    • 5.7.2. Jednoelementowe krotki wymagają przecinka 89
    • 5.7.3. Pakowanie i rozpakowywanie krotek 90
    • 5.7.4. Konwertowanie pomiędzy listami i krotkami 91
  • 5.8. Zbiory 92
    • 5.8.1. Działania na zbiorach 92
    • 5.8.2. Frozenset 93
  • Podsumowanie 93

Rozdział 6. Łańcuchy znaków 95

  • 6.1. Łańcuchy znaków jako sekwencje znaków 95
  • 6.2. Podstawowe działania na łańcuchach znaków 96
  • 6.3. Znaki specjalne i znaki ucieczki 96
    • 6.3.1. Podstawowe sekwencje specjalne 97
    • 6.3.2. Numeryczne sekwencje specjalne i znaki Unicode 97
    • 6.3.3. Drukowanie i rozwijanie łańcuchów znaków ze znakami specjalnymi 98
  • 6.4. Metody łańcuchów znaków 99
    • 6.4.1. Metody split i join 99
    • 6.4.2. Konwersja łańcuchów znaków na liczby 100
    • 6.4.3. Usuwanie dodatkowych białych znaków 101
    • 6.4.4. Przeszukiwanie łańcuchów znaków 102
    • 6.4.5. Modyfikowanie łańcuchów znaków 104
    • 6.4.6. Zmienianie łańcuchów znaków przy użyciu operacji na listach 105
    • 6.4.7. Przydatne metody i stałe 106
  • 6.5. Konwersja obiektów na łańcuchy znaków 107
  • 6.6. Korzystanie z metody format 108
    • 6.6.1. Metoda format i parametry pozycyjne 109
    • 6.6.2. Metoda format i parametry wskazywane po nazwie 109
    • 6.6.3. Specyfikatory formatowania 110
  • 6.7. Formatowanie łańcuchów znaków przy użyciu % 110
    • 6.7.1. Korzystanie z sekwencji formatowania 111
    • 6.7.2. Parametry przekazywane przez nazwę i sekwencje formatujące 112
  • 6.8. Interpolacja łańcuchów znaków 112
  • 6.9. Typ bytes 113
  • Podsumowanie 115

Rozdział 7. Słowniki 117

  • 7.1. Czym jest słownik? 117
  • 7.2. Inne działania na słownikach 119
  • 7.3. Liczenie słów 122
  • 7.4. Co może być kluczem słownika? 123
  • 7.5. Macierze rzadkie 124
  • 7.6. Słowniki jako pamięć podręczna 125
  • 7.7. Wydajność słowników 126
  • Podsumowanie 127

Rozdział 8. Przepływ sterowania 129

  • 8.1. Pętla while 129
  • 8.2. Instrukcja if-elif-else 130
  • 8.3. Pętla for 132
    • 8.3.1. Funkcja range 132
    • 8.3.2. Ograniczenie funkcji range poprzez wartość początkową i krok 133
    • 8.3.3. Używanie instrukcji break oraz continue w pętlach for 133
    • 8.3.4. Pętla for i rozpakowywanie krotek 133
    • 8.3.5. Funkcja enumerate 134
    • 8.3.6. Funkcja zip 134
  • 8.4. Listy i słowniki składane 135
    • 8.4.1. Wyrażenia generatora 136
  • 8.5. Instrukcje, bloki i wcięcia 136
  • 8.6. Wartości i wyrażenia logiczne 139
    • 8.6.1. Obiekty jako wartości logiczne 139
    • 8.6.2. Porównania i operatory logiczne 140
  • 8.7. Prosty program analizujący plik tekstowy 141
  • Podsumowanie 142

Rozdział 9. Funkcje 143

  • 9.1. Podstawy definiowania funkcji 143
  • 9.2. Opcje parametrów funkcji 144
    • 9.2.1. Parametry pozycyjne 145
    • 9.2.2. Przekazywanie argumentów przez nazwę parametru 146
    • 9.2.3. Zmienna liczba argumentów 147
    • 9.2.4. Łączenie technik przekazywania argumentów 148
  • 9.3. Obiekty mutowalne jako argumenty 148
  • 9.4. Zmienne lokalne, nielokalne i globalne 149
  • 9.5. Przypisywanie funkcji do zmiennych 151
  • 9.6. Wyrażenia lambda 152
  • 9.7. Funkcje generatorów 152
  • 9.8. Dekoratory 154
  • Podsumowanie 155

Rozdział 10. Moduły i zakresy 157

  • 10.1. Czym jest moduł? 157
  • 10.2. Pierwszy moduł 158
  • 10.3. Instrukcja import 161
  • 10.4. Ścieżka szukania modułów 161
    • 10.4.1. Gdzie umieszczać własne moduły 162
  • 10.5. Nazwy prywatne w modułach 163
  • 10.6. Biblioteka i moduły zewnętrzne 164
  • 10.7. Zasięg zmiennych i przestrzenie nazw w Pythonie 165
  • Podsumowanie 171

Rozdział 11. Programy w Pythonie 173

  • 11.1. Tworzenie bardzo prostego programu 174
    • 11.1.1. Uruchamianie skryptu z wiersza poleceń 174
    • 11.1.2. Argumenty wiersza poleceń 175
    • 11.1.3. Przekierowywanie wejścia i wyjścia skryptu 175
    • 11.1.4. Moduł argparse 176
    • 11.1.5. Używanie modułu fileinput 177
  • 11.2. Tworzenie skryptów bezpośrednio wykonywalnych w systemie UNIX 179
  • 11.3. Skrypty w systemach macOS 180
  • 11.4. Możliwości wykonywania skryptów w systemach Windows 180
    • 11.4.1. Uruchamianie skryptu z wiersza poleceń lub poprzez PowerShell 180
    • 11.4.2. Inne możliwości w systemach Windows 181
  • 11.5. Programy i moduły 181
  • 11.6. Dystrybucja aplikacji w Pythonie 186
    • 11.6.1. Pakiety wheel 186
    • 11.6.2. zipapp oraz pex 186
    • 11.6.3. py2exe oraz py2app 187
    • 11.6.4. Tworzenie programów wykonywalnych za pomocą freeze 187
  • Podsumowanie 188

Rozdział 12. Praca z systemem plików 189

  • 12.1. os i os.path a pathlib 190
  • 12.2. Ścieżki i nazwy ścieżek 190
    • 12.2.1. Ścieżki bezwzględne i względne 191
    • 12.2.2. Bieżący katalog roboczy 192
    • 12.2.3. Poruszanie się po katalogach przy pomocy pathlib 193
    • 12.2.4. Operacje na nazwach ścieżek 193
    • 12.2.5. Operacje na nazwach ścieżek przy użyciu pathlib 195
    • 12.2.6. Użyteczne stałe i funkcje 196
  • 12.3. Uzyskiwanie informacji o plikach 198
    • 12.3.1. Uzyskiwanie informacji o plikach przy użyciu scandir 199
  • 12.4. Więcej operacji w systemie plików 199
    • 12.4.1. Więcej operacji w systemie plików przy użyciu pathlib 201
  • 12.5. Obsługa wszystkich plików w części drzewa katalogów 202
  • Podsumowanie 203

Rozdział 13. Pisanie i czytanie plików 205

  • 13.1. Otwieranie plików i obiektów typu file 205
  • 13.2. Zamykanie plików 206
  • 13.3. Otwieranie plików w różnych trybach 207
  • 13.4. Funkcje do czytania i pisania danych tekstowych lub binarnych 207
    • 13.4.1. Używanie trybu binarnego 209
  • 13.5. Czytanie i pisanie przy pomocy pathlib 210
  • 13.6. Operacje wejścia/wyjścia i przekierowania 210
  • 13.7. Przekierowanie binarnych struktur danych i moduł struct 213
  • 13.8. Serializacja obiektów do plików 215
    • 13.8.1. Argumenty przeciw serializacji 217
  • 13.9. Magazynowanie obiektów przy użyciu modułu shelve 218
  • Podsumowanie 220

Rozdział 14. Wyjątki 221

  • 14.1. Wstęp do wyjątków 221
    • 14.1.1. Ogólna koncepcja błędów i obsługi wyjątków 222
    • 14.1.2. Bardziej formalna definicja wyjątku 224
    • 14.1.3. Obsługa różnych typów wyjątków 225
  • 14.2. Wyjątki w Pythonie 225
    • 14.2.1. Typy wyjątków w Pythonie 226
    • 14.2.2. Zgłaszanie wyjątków 228
    • 14.2.3. Łapanie i obsługa wyjątków 229
    • 14.2.4. Definiowanie nowych wyjątków 230
    • 14.2.5. Debugowanie programów przy użyciu instrukcji assert 231
    • 14.2.6. Hierarchia dziedziczenia wyjątków 232
    • 14.2.7. Przykład: program do pisania danych na dysku w Pythonie 232
    • 14.2.8. Przykład: wyjątki w zwykłych przeliczeniach 233
    • 14.2.9. Kiedy używać wyjątków? 234
  • 14.3. Managery kontekstu i słowo kluczowe with 235
  • Podsumowanie 236

CZĘŚĆ III. ZAAWANSOWANE CECHY JĘZYKA 237

Rozdział 15. Klasy i programowanie zorientowane obiektowo 239

  • 15.1. Definiowanie klas 239
    • 15.1.1. Wykorzystanie instancji klasy jako struktury lub rekordu 240
  • 15.2. Zmienne instancji 241
  • 15.3. Metody 241
  • 15.4. Zmienne klasy 243
    • 15.4.1. Zagwozdka związana ze zmiennymi klasy 244
  • 15.5. Metody statyczne i metody klas 245
    • 15.5.1. Metody statyczne 246
    • 15.5.2. Metody klas 247
  • 15.6. Dziedziczenie 248
  • 15.7. Dziedziczenie i zmienne klasowe oraz zmienne instancji 250
  • 15.8. Powtórka: podstawy klas w Pythonie 251
  • 15.9. Zmienne i metody prywatne 253
  • 15.10. @property i bardziej elastyczne zmienne instancji 254
  • 15.11. Zasięg i przestrzenie nazw dla instancji klas 255
  • 15.12. Destruktory i zarządzanie pamięcią 259
  • 15.13. Wielodziedziczenie 260
  • Podsumowanie 262

Rozdział 16. Wyrażenia regularne 263

  • 16.1. Co to jest wyrażenie regularne? 263
  • 16.2. Wyrażenia regularne ze znakami specjalnymi 264
  • 16.3. Wyrażenia regularne i łańcuchy znaków 265
    • 16.3.1. Raw stringi 266
  • 16.4. Uzyskiwanie dostępu do dopasowanego tekstu w łańcuchu znaków 267
  • 16.5. Zastępowanie tekstu wyrażeniem regularnym 270
  • Podsumowanie 272

Rozdział 17. Typy danych jako obiekty 273

  • 17.1. Typy również są obiektami 273
  • 17.2. Korzystanie z typów 274
  • 17.3. Typy i klasy zdefiniowane przez użytkownika 274
  • 17.4. Duck typing 276
  • 17.5. Czym jest specjalny atrybut metody? 277
  • 17.6. Obiekty zachowujące się jak listy 278
  • 17.7. Atrybut metody __getitem__ 279
    • 17.7.1. Jak to działa? 280
    • 17.7.2. Implementacja kompletu funkcjonalności listy 281
  • 17.8. Obiekt o wszystkich możliwościach listy 281
  • 17.9. Klasy pochodne od typów wbudowanych 283
    • 17.9.1. Pochodne od listy 283
    • 17.9.2. Pochodne klasy UserList 284
  • 17.10. Kiedy korzystać ze specjalnych atrybutów metod? 285
  • Podsumowanie 286

Rozdział 18. Pakiety 287

  • 18.1. Czym jest pakiet? 287
  • 18.2. Pierwszy przykład 288
  • 18.3. Konkretny przykład 289
    • 18.3.1. Pliki __init__ w pakietach 291
    • 18.3.2. Podstawowe użycie pakietu matproj 291
    • 18.3.3. Ładowanie subpakietów i submodułów 291
    • 18.3.4. Instrukcja import wewnątrz pakietów 292
  • 18.4. Atrybut __all__ 293
  • 18.5. Właściwe korzystanie z pakietów 294
  • Podsumowanie 295

Rozdział 19. Korzystanie z bibliotek Pythona 297

  • 19.1. "Wszystko w standardzie" - biblioteka standardowa 298
    • 19.1.1. Praca z różnymi typami danych 298
    • 19.1.2. Operacje na plikach i pamięci 298
    • 19.1.3. Dostęp do usług systemu operacyjnego 300
    • 19.1.4. Korzystanie z protokołów i formatów internetu 300
    • 19.1.5. Narzędzia do tworzenia i debugowania oraz usługi uruchomieniowe 301
  • 19.2. Wyjście poza bibliotekę standardową 301
  • 19.3. Dodawanie kolejnych bibliotek w Pythonie 302
  • 19.4. Instalowanie bibliotek Pythona przy użyciu pip oraz venv 302
    • 19.4.1. Instalacja z flagą --user 303
    • 19.4.2. Środowiska wirtualne 303
  • 19.5. PyPI (czyli The Cheese Shop) 304
  • Podsumowanie 304

CZĘŚĆ IV. PRACA Z DANYMI 305

Rozdział 20. Podstawy obsługi plików 307

  • 20.1. Problem: niekończący się napływ plików z danymi 307
  • 20.2. Scenariusz: dane produktowe z piekła 308
  • 20.3. Więcej organizacji 310
  • 20.4. Oszczędzanie miejsca: kompresja i sprzątanie 311
    • 20.4.1. Kompresja 311
    • 20.4.2. Sprzątanie plików 312
  • Podsumowanie 314

Rozdział 21. Procesowanie plików danych 315

  • 21.1. Witamy w ETL 315
  • 21.2. Czytanie plików tekstowych 316
    • 21.2.1. Kodowanie tekstu: ASCII, Unicode itp. 316
    • 21.2.2. Tekst nieustrukturyzowany 318
    • 21.2.3. Pliki płaskie podzielone znakami specjalnymi 320
    • 21.2.4. Moduł csv 322
    • 21.2.5. Czytanie pliku CSV jako listy słowników 324
  • 21.3. Pliki Excel 324
  • 21.4. Czyszczenie danych 326
    • 21.4.1. Czyszczenie 326
    • 21.4.2. Sortowanie 327
    • 21.4.3. Problemy i pułapki czyszczenia danych 328
  • 21.5. Pisanie plików z danymi 329
    • 21.5.1. CSV i pliki dzielone znakami specjalnymi 329
    • 21.5.2. Zapisywanie plików Excel 330
    • 21.5.3. Pakowanie plików danych 331
  • Podsumowanie 331

Rozdział 22. Dane w sieci 333

  • 22.1. Pobieranie plików 333
    • 22.1.1. Korzystanie z Pythona do pobierania plików z serwera FTP 334
    • 22.1.2. Pobieranie plików przy użyciu SFTP 335
    • 22.1.3. Pobieranie plików przy użyciu HTTP/HTTPS 336
  • 22.2. Pobieranie danych przez API 337
  • 22.3. Ustrukturyzowane formaty danych 339
    • 22.3.1. Dane w formacie JSON 339
    • 22.3.2. Dane XML 342
  • 22.4. Sczytywanie danych z sieci WWW 347
  • Podsumowanie 351

Rozdział 23. Przechowywanie plików 353

  • 23.1. Relacyjne bazy danych 354
    • 23.1.1. Bazodanowe API Pythona 354
  • 23.2. SQLite: korzystanie z bazy danych SQLite 354
  • 23.3. Używanie MySQL, PostgreSQL i innych relacyjnych baz danych 357
  • 23.4. Ułatwienie pracy z bazą danych - ORM 357
    • 23.4.1. SQLAlchemy 358
    • 23.4.2. Wykorzystanie Alembic do zmian struktury bazy danych 361
  • 23.5. Nierelacyjne bazy danych 364
  • 23.6. Klucz-wartość i Redis 364
  • 23.7. Dokumenty w MongoDB 367
  • Podsumowanie 370

Rozdział 24. Badanie danych 371

  • 24.1. Narzędzie do badania danych 371
    • 24.1.1. Zalety Pythona w zakresie obsługi danych 371
    • 24.1.2. Python może być lepszy niż arkusz kalkulacyjny 372
  • 24.2. Notatnik Jupyter 372
    • 24.2.1. Uruchomienie jądra 373
    • 24.2.2. Wykonanie kodu w komórce 373
  • 24.3. Python i pandas 375
    • 24.3.1. Dlaczego mógłbyś chcieć używać pandas? 375
    • 24.3.2. Instalacja pandas 375
    • 24.3.3. Ramki danych 376
  • 24.4. Czyszczenie danych 377
    • 24.4.1. Ładowanie i zachowywanie danych w pandas 377
    • 24.4.2. Czyszczenie danych i ramki danych 379
  • 24.5. Agregowanie danych i manipulowanie nimi 381
    • 24.5.1. Łączenie ramek danych 382
    • 24.5.2. Wybieranie danych 383
    • 24.5.3. Grupowanie i agregacja 384
  • 24.6. Obrazowanie danych 385
  • 24.7. Kiedy nie używać biblioteki pandas? 386
  • Podsumowanie 387

Studium przypadku 389

  • Pobranie danych 389
  • Parsowanie danych dat pomiarów 392
  • Wybór stacji na podstawie długości i szerokości geograficznej 393
  • Wybór stacji i uzyskanie jej metadanych 395
  • Pozyskanie i sparsowanie danych pogodowych 397
    • Pozyskanie danych 397
    • Parsowanie danych pogodowych 397
  • Zapisywanie danych pogodowych do bazy danych (opcjonalne) 400
  • Wybieranie i obrazowanie danych 401
  • Użycie pandas do tworzenia wykresu 401

Dodatek A. Przewodnik po dokumentacji Pythona 403

Dodatek B. Odpowiedzi do ćwiczeń 425

Skorowidz 467

  • Tytuł: Python. Szybko i prosto. Wydanie III
  • Autor: Naomi Ceder
  • Tytuł oryginału: The Quick Python Book, 3rd Edition
  • Tłumaczenie: Katarzyna Bogusławska
  • ISBN: 978-83-283-3772-5, 9788328337725
  • Data wydania: 2019-04-02
  • Format: Ebook
  • Identyfikator pozycji: pyszy3
  • Wydawca: Helion