Задачи на generics в Dart. Часть 4
Сделайте TreeNode<T> generic class с полем значения и списком дочерних узлов.
Сделайте generic-функцию flatten для списка списков: List<T> flatten<T>(List<List<T>> lists).
Сделайте sealed/иерархию Either<L, R> с вариантами Left<L, R> и Right<L, R>. Добавьте метод fold (или when), который принимает два обработчика. Проверьте на функции парсинга числа: успех — Right, ошибка — Left со строкой.
// Either<String, int> parse(String s) { ... }
Сделайте generic-функцию с nullable bound: T? firstOrNull<T>(List<T> list) — верните первый элемент или null для пустого списка.
Сделайте Mapper<T, R> typedef и используйте его в функции mapList.
Сделайте generic-метод в non-generic class: класс Box с методом T unwrap<T>(Object value) (или аналогичным).
Сделайте Paginated<T> для API response: поля items, page, totalPages.
Сравните List<dynamic> и List<Object?>: покажите разницу в проверках типов при чтении элементов.
Generic-функция zip двух списков: List<(A, B)> zip<A, B>(List<A> a, List<B> b) до минимальной длины.
Комплексная generic-задача: реализуйте простой Cache<K, V> на Map с методами get, put и getOrPut.