Hierarchia własnych wyjątków
Treść zadania
Zdefiniuj własne wyjątki tworzące hierarchię:
BladDanych— dziedziczy po wbudowanej klasieException; ogólny błąd danych wejściowych,BladFormatu— dziedziczy poBladDanych; dane mają zły format,BladZakresu— dziedziczy poBladDanych; format jest dobry, ale wartość jest spoza dozwolonego zakresu.
Napisz funkcję parsuj_godzine(tekst), która zamienia godzinę zapisaną w postaci GG:MM na liczbę minut od północy ($60 \cdot GG + MM$). Funkcja sprawdza dane w tej kolejności:
- Jeśli
tekstnie ma dokładnie 5 znaków, na pozycji 2 nie ma dwukropka albo znaki na pozycjach 0, 1, 3, 4 nie są cyframi — zgłaszaBladFormatu("oczekiwano formatu GG:MM"). - Jeśli godzina jest większa od 23 — zgłasza
BladZakresu("godzina spoza zakresu 0-23"). - Jeśli minuty są większe od 59 — zgłasza
BladZakresu("minuty spoza zakresu 0-59").
Program dla każdej wczytanej linii wywołuje parsuj_godzine i wypisuje wynik albo informację o błędzie. Oba rodzaje błędów przechwytuje jedną klauzulą except BladDanych as e — łapie ona wyjątki klasy BladDanych i wszystkich klas, które po niej dziedziczą.
Dane wejściowe
- 1. linia: liczba napisów $n$
- kolejne $n$ linii: napis do sprawdzenia (bez spacji)
Dane wyjściowe
Dla każdego napisu jedna linia:
<napis> -> <minuty>— jeśli napis jest poprawny,<napis> -> <NazwaKlasyWyjątku>: <komunikat>— jeśli funkcja zgłosiła wyjątek, np.24:00 -> BladZakresu: godzina spoza zakresu 0-23.
Ograniczenia
- $1 \le n \le 50$
- Każdy napis ma od 1 do 20 znaków.
Uwagi
- Własny wyjątek to zwykła klasa dziedzicząca po
Exception— zwykle nie potrzebuje żadnego kodu:class BladDanych(Exception): pass. Komunikat przekazuje się przy zgłaszaniu:raise BladFormatu("…"). - Nazwę klasy przechwyconego wyjątku odczytasz wyrażeniem
type(e).__name__. - Gdy błędy różnych klas trzeba obsłużyć różnie, piszemy kilka klauzul
except. Python sprawdza je po kolei i wybiera pierwszą pasującą, dlatego klasy potomne muszą stać przed klasą bazową:
```python
try:
minuty = parsuj_godzine(tekst)
except BladFormatu:
... # tylko błędy formatu
except BladDanych:
... # wszystkie pozostałe błędy danych (np. BladZakresu)`
Gdybyexcept BladDanychstało pierwsze, przechwyciłoby takżeBladFormatu, a druga klauzula nigdy by się nie wykonała. "07".isdigit()sprawdza, czy napis składa się z samych cyfr.
Przykład
5 07:30 23:59 24:00 7:30 12:60
07:30 -> 450 23:59 -> 1439 24:00 -> BladZakresu: godzina spoza zakresu 0-23 7:30 -> BladFormatu: oczekiwano formatu GG:MM 12:60 -> BladZakresu: minuty spoza zakresu 0-59
Potrzebujesz teorii?
Zasady obowiązujące w rozdziale 19
Zadania w tym rozdziale uczą dziedziczenia: klasa potomna przejmuje atrybuty i metody klasy bazowej, może je nadpisać (override) albo rozszerzyć, wywołując wersję z klasy bazowej przez super(). Dzięki polimorfizmowi ten sam kod (np. pętla po liście obiektów) wywołuje metodę odpowiednią dla konkretnej klasy obiektu. Dziedziczenie przydaje się też przy wyjątkach: własne wyjątki to klasy dziedziczące po Exception, które można układać w hierarchie.
Konwencje wspólne:
- Każde zadanie to osobny program: czyta standardowe wejście i wypisuje wynik na standardowe wyjście.
- W każdym zadaniu dostajesz kod startowy ze szkieletami klas i gotowym wczytywaniem danych. Twoim zadaniem jest uzupełnienie klas — wynik programu zależy od tego, jak działają Twoje klasy.
- Nazwy klas i metod podane w treści są obowiązkowe (kod startowy z nich korzysta). Nazwy w kodzie piszemy bez polskich znaków, np.
Kolo,Czlowiek. - „Z dokładnością do 2 miejsc po przecinku” oznacza dokładnie dwie cyfry po kropce, np.
f"{x:.2f}"(3.00,4.50). - Program nie wypisuje komunikatów typu „Podaj liczbę:”.
Zadanie pochodzi z otwartego zbioru Nauka-Programowania (z rozwiązaniami wzorcowymi). Zgłoś błąd w treści lub testach.
Przywrócono Twój zapisany kod.
Python uruchomi się w przeglądarce przy pierwszym teście.
Kod zapisuje się automatycznie w tej przeglądarce. Tab wstawia wcięcie; aby opuścić edytor klawiaturą, naciśnij Esc, a potem Tab.
Testy
Program dostaje „Wejście” przez input() i musi wypisać „Oczekiwane wyjście”. Liczby porównywane są z tolerancją 0,01, a tekst podany w input("…") nie jest sprawdzany.
Test 1
Nie uruchomiono1 00:00
00:00 -> 0
Test 2
Nie uruchomiono2 ab:cd 12-30
ab:cd -> BladFormatu: oczekiwano formatu GG:MM 12-30 -> BladFormatu: oczekiwano formatu GG:MM
Test 3
Nie uruchomiono3 99:99 12:345 00:59
99:99 -> BladZakresu: godzina spoza zakresu 0-23 12:345 -> BladFormatu: oczekiwano formatu GG:MM 00:59 -> 59
Test 4
Nie uruchomiono4 13:05 1305 23:60 :1234
13:05 -> 785 1305 -> BladFormatu: oczekiwano formatu GG:MM 23:60 -> BladZakresu: minuty spoza zakresu 0-59 :1234 -> BladFormatu: oczekiwano formatu GG:MM
Test 5
Nie uruchomiono2 12:3a 18:45
12:3a -> BladFormatu: oczekiwano formatu GG:MM 18:45 -> 1125