11.08 Наследование и исключения
— пример из лекции
Наследование
Видимость полей в цепочке наследования
Задать класс A с полем A.v = 1, класс B(A) с полем B.v = 2 и объект b = B() с полем b.v = 3. Посмотреть, чему будет равно b.v до и после удаления .v сначала из объекта b, а затем из класса B.
Проблема порождения нового объекта (например, суммы) базового класса при выполнении унаследованной операции над объектами производного класса
Пофиксить проблему с помощью self.__class__ на примере из демонстрации
Защита от коллизии имён
- Множественное наследование.
Пример невалидного наследования
class A: pass class B(A): pass class Y(B, A): pass class X(A, B): pass
Ломаем MRO.
- Определены следующие четыре класса:
class A: pass class B: pass class C(A, B): pass class D(B, A): pass
Тремя разными способами определите класс E, один из предков которого (необязательно первый) - класс C, а другой - один из оставшихся трех классов. При этом наследование должно быть невалидным, т.е. приводить к диагностике "TypeError: Cannot create a consistent method resolutionorder (MRO)"
- Для каждого из трех способов "почините" MRO, не изменяя множество предков ни у какого класса (хинт: множество - штука неупорядоченная)
- В каких случаях MRO удалось "починить", вообще не трогая классы A, B, C, D?
super()
Например, дёрнуть «родительский» __init__()
Линейно унаследовать A → B → C, так, чтобы объект.__str__() выводил путь по дереву наследования, например "A:B" для print(B())
Исключения
Иерархия исключений
Программа, которая заставляет человека вводить что-либо до тех пор, пока он не введёт целое число (int(input()))
- Исключение — это не «ошибка», а нелинейная передача управления
напишите функцию div_ab(a,b), которая делит первый аргумент на второй; напишите цикл по кортежу из пар чисел, в цикле выводится результат div_ab() для очередной пары, а также ловится исключение ZeroDivisionError, при обработке которого выводится текст "inf". Проверьте работу цикла на кортеже ((10,2),(1,0),(9,3)).
Вброс исключений
О дистанционных тестах.
Д/З
Дистанционные тесты. TODO написать более подробный пример
Ко всем задачам (если это не оговорено отдельно) подобрать среди зарегистрированных репозиториев три каталога с тестами, которые
В каталог с решением каждой задачи положить файл URLS (большими буквами), в котором должно быть три таких URL, по одному в строке
Пример строчки в таком файле для текстов из репозитория на GitHub:
https://github.com/Veniamin-Arefev/pythonprac-2021/tree/main/20211111/2/tests
Пример для GitLab:
https://git.cs.msu.ru/s02190248/pythonprac/-/tree/main/20211111/2/tests
Проверить что эти тесты скачиваются и проверяются pyjydge
Задача_1:
Написать класс DivStr (унаследованный от collections.UserString), в котором:
Добавлена возможность заведения пустой строки без параметров — DivStr()
Добавлена операция a // n — возвращается итератор из n подстрок одинакового наибольшего размера, на которые можно разбить исходную строку
Добавлена операция a % n — возвращается «остаток от деления», хвостик, который надо приписать к a // n, чтобы получилась вся строка (возможно, пустой)
Input
Output
XcDf QWEa sdER Tdfg RTY ERT dfg RTY y cD fQ WE gRTYY
Задача_2:
Написать программу, которая заставляет человека вводить координаты вершин треугольника в формате (x1, y1), (x2, y2), (x3, y3), до тех пор, пока это не окажутся координаты вершин треугольника в указанном формате, а потом выводит его площадь с точностью до сотой.
Если формат ввода неправильный, программа вместо площади выводит «Invalid input», а если формат условно правильный, но площадь его нулевая или вычислить её нельзя, потому что введены вообще не числа — «Not a triangle».
Диагностика ввода и расчет площади производится в функции triangleSquare, которая:
- получает на вход входную строку программы
преобразует строку в координаты вершин: (x1, y1), (x2, y2), (x3, y3) = eval(inStr)
при преобразовании ловит все исключения, и при любом перехваченном исключении формирует исключение InvalidInput (этот класс нужно определить)
если ввод корректен, выполняет проверку на то, что координаты - корректны для треугольника; в случае некорректности формирует исключение BadTriangle (этот класс нужно определить)
- если координаты корректны, то вычисляет и возвращает площадь
При вызове функции triangleSquare в основном коде программы ловятся исключения InvalidInput и BadTriangle, и в блоках их обработки выдается соответствующая диагностика
Вывод площади выполняется в блоке else
- Написать тесты:
- на неправильный формат
- на не-треугольник
Input:
asdf 1,2,3,4,5,6 (1,1), (2,2), (11,11) (1,2), (4,5), (9,8)
Output:
Invalid input Invalid input Not a triangle 3.00
Задача_3 на иерархию исключений
- Написать программу, в которой есть:
Несложная иерархия исключений: базовый класс Undead и наследники Skeleton, Zombie и Ghoul
Функция necro(a), которая в зависимости от остатка от деления a на 3 формирует исключение: 0 - Skeleton, 1 - Zombie, 2 - Ghoul
Ввод целочисленных значений x и y
Цикл по range(x,y), в теле цикла: вызов necro(), перехват исключений следующих типов (и в таком порядке): Skeleton, Zombie, Undead; при обработке исключений вывод текста, соответственно, "Skeleton", "Zombie", "Generic Undead"
Input:
11, 17
Output:
Generic Undead Skeleton Zombie Generic Undead Skeleton Zombie
- Написать программу, в которой есть: