SPBU-Homework-4
Here you can find conditions and solutions to problems for the fourth semester.
Navigation menu
- Semester №1
- Semester №2
- Semester №3
- Semester №4 ⬅️ You are here
Homework
Homework №1
-
Реализовать функции для работы с векторами (скалярное произведение, вычисление длины, нахождение угла между ними) и матрицами (транспонирование, сложение, произведение). Где возможно, реализовать "в одну строчку".
-
Реализовать функции, имитирующие работу bash команд --- wc, nl, head, tail.
Homework №2
-
Каррирование
Частичное применение (каррирование, curry) --- это превращение функции от нескольких параметров в функцию от одного параметра, возвращающую функцию от остальных параметров. К ней существует обратная операция -- uncarry. В Python каррирование в таком виде затруднено из-за произвольной арности.
Напишите функцию
curry_explicit(function, arity)
и парную к нейuncurry_explicit(function, arity)
.Требования\допущения:
- Пользователь верно указал арность переданной функции.
- Если он ошибся, то бросить исключение. Можно здесь посмотреть что это и как с этим работать. Здесь имеется в виду отслеживание простых ситуаций вида: пользователь указал, что функция от 1 аргумента, а передает 5 или же передает аргументы и указывает, что арность -- ноль. НЕ требуется проверки, действительно ли передана функция от трех аргументов, если передали арность = 3.
- Отрицательная арность невозможна -- бросить исключение.
- При арности 0 результатом будет функция от 0 параметров:
curry_explicit(f,0)() == f()
. - При арности 1 -- функция от 1 параметра:
curry_explicit(f,1)(x) == f(x)
. - Не забудьте, что есть произвольно-арные функции, такие как
print()
;curry_explicit
должна замораживать их арность, т.е. нельзя написатьcurry_explicit(print,2)(1)(2)(3,4,5)
. В данном случаеcurry_explicit(print,2)(1)(2)
вернетNone
, что сделает невозможным дальнейшее применение (Python сам бросит ошибку, данный кейс отдельно обрабатывать не нужно) - Именованные аргументы поддерживать не нужно.
Пример работы:
f2 = curry_explicit((lambda x, y, z: f'<{x}, {y}, {z}>'), 3) g2 = uncurry_explicit(f2, 3) print(f2(123)(456)(562)) # <123, 456, 562> print(g2(123, 456, 562)) # <123, 456, 562>
-
Кэширование
Реализовать декоратор для кеширования результатов выполнения функции. То есть необходимо сохранять результаты вычислений для разного набора аргументов функции. Аргумент декоратора -- сколько последних результатов хранить. По умолчанию ничего не кэшируется. Необходимо поддержать как неименованные аргументы, так и именованные.
-
Типы аргументов
Напишите декоратор
@smart_args
, который анализирует типы значений по умолчанию аргументов функции и, в зависимости от этого, копирует и/или вычисляет их перед выполнением функции:Evaluated(func_without_args)
--- подставляет значение по умолчанию, вычисляемое в момент вызова. В качестве аргумента принимает функцию БЕЗ аргументов, которая что-то возвращает. Например она может менять глобальный счетчик или что-то считать внутри класса. Во время работы необходимо вызвать эту функцию и использовать значение, которое будет получено в результате выполнения.Isolated()
--- это фиктивное значение по умолчанию; аргумент должен быть передан, но в момент передачи -- скопирован (глубокая копия).
Также напишите определения
Evaluated
иIsolated
.Требования\допущения:
- Необходима поддержка только именованных аргументов.
- Не нужно сочетать
Isolated
иEvaluated
. - Добавьте проверки (
assert
) того, что пользователь случайно не вышел за эти рамки (используетIsolated
иEvaluated
в сочетании или пытается их использовать для позиционных аргументов).
Примеры работы:
Для
Isolated
:@smart_args def check_isolation(*, d=Isolated()): d['a'] = 0 return d no_mutable = {'a': 10} print(check_isolation(d=no_mutable)) # {'a': 0} print(no_mutable) # {'a': 10}
Для
Evaluated
:import random def get_random_number(): return random.randint(0,100) # Для x дефолтное значение всегда будет одинаковое, оно вычислится один раз # Для y дефолтное значение может быть разным, так как оно будет # вычисляться КАЖДЫЙ раз, если не передано значение y @smart_args def check_evaluation(*, x=get_random_number(), y=Evaluated(get_random_number)): print(x, y) check_evaluation() # 15 36 check_evaluation() # 15 66 check_evaluation() # 15 51 check_evaluation(y=150) # 15 150
Homework №3
-
Анализ таблицы:
- Визуализировать базовую статистику таблицы. В каком классе было больше всего пассажиров?
- Группировать таблицу в два уровня: класс и пол, по среднему значению возраста. Кто из возможных комбинаций самый юный, кто самый взрослый? Насколько отличаются эти значения?
- Отобрать только выживших пассажиров с фамилией, начинающейся на “K”. Отсортировать их по убыванию стоимости билета. Кто заплатил больше всех? Кто меньше всех?
- Какое максимальное количество родных было с выжившим пассажиром?
- Посчитайте среднюю стоимость билета пассажиров, для которых указана каюта (Cabin) и для тех, у кого она не указана, во сколько раз они отличаются?
-
Визуализация: необходимо построить по данным таблицам 10 различных графиков.
Homework №4
-
Подготовка данных:
- Получите датасет iris представьте его как одномерный / двумерный массивы (признаки поместить в матрицу
[n; 4]
и названия самого ириса в вектор длиныn
), отобразите сколько места он занимает в памяти. - Нормализуйте данные на промежуток от 0 до 1 для каждой колонки.
- Представьте один из признаков в виде категориальной переменной --- разделите ее на 3 типа используя квантили:
- < 0.25 -- small
- 0.025-0.75 -- medium
- > 0.75 -- big
- Разделите датасет на две случайные выборки (0.8 / 0.2).
- Получите датасет iris представьте его как одномерный / двумерный массивы (признаки поместить в матрицу
-
Анализ данных:
- Выберете один из методов классификации (например SVM), обучите на тренировочном датасете, проверьте на тестовом и сделайте выводы.
- Проведите три эксперимента изменяя гиперпараметры модели или условия препроцессинга данных (например, нормализованные или нет данные), сделайте выводы.
- Пользуясь методами уменьшения размерности (PCA, t-sne) визуализируйте датасет. Это должен быть scatter plot, где точка это отдельный ирис, ее координаты --- признаки со сжатой выбранной вам размерностью, а цвет --- тип ириса. Нарисуйте этот график дважды, где
- Тип ириса вы берете из оригинальных данных
- Тип ириса вы берете из предсказанных данных
Homework №5
Реализуйте декартово дерево. Требования:
- Структура должна реализовывать
MutableMapping
. - Реализуйте прямой и обратный итераторы (
__iter__
возвращает прямой). - Взаимодействие с элементами через
[]
. - Проверку ключа через оператор
in
.
Homework №6
Реализовать семафор через менеджер контекстов (доступ к объекту через with
). Написать тесты для него используя многопоточность.
Homework №8
Рeализовать сервис по обработке изображения. Серверная часть должна принимать картинку и обрабатывать одним из предложенных алгоритмов. Клиентская часть предоставляет форму загрузки изображения, а так же показывает картинку до и после обработки.
NLTK-Report
Exam
Test
- Напишите декоратор
@spy
и функциюprint_usage_statistic(function: Callable)
, которая выдает генератор кортежей из двух элементов: времени запуска (во сколько запускали) функциюfunction
и параметров, с которыми она была запущена. Для работы функцииprint_usage_statistic
необходимо, чтобы функция была декорирована, если это не так, то пользователь должен получить соответствующее сообщение.
@spy
def foo(num):
print(num)
if __name__ == '__main__':
foo(30)
foo("hello")
foo(5)
for (time, parameters) in print_usage_statistic(foo):
str_parameters = ", ".join(
f"{k} = {v}" for k, v in parameters.items()
)
print(
f"function {foo.__name__} was called at {time} "
f"with parameters:\n{str_parameters}"
)
- Напишите функцию правой свёртки
reduce_right(function, values, [initial])
. Необходимо написать свою, использовать встроенныйreduce
нельзя. Использовать рекурсию также нельзя – последовательность данных может быть достаточно длинной, чтобы влезть в память (миллион чисел), но не влезть в стек вызовов функций (он обычно ограничен несколькими тысячами). Последовательность может быть не только списком, кортежом или строкой, но и совершенно произвольной, например, открытым файлом (который читается построчно).
Примеры работы:
Input:
print(reduce_right(lambda x, y: f'({x}+{y})', 'abcde'))
Output:
(a+(b+(c+(d+e))))
Input:
print(reduce_right(
lambda x, y: f'({x}+{y})',
(ord(c) for c in 'abcde')
))
Output:
(97+(98+(99+(100+101))))