Домашняя работа по курсу
- Домашняя работа нужна в первую очередь для того, чтобы доказать себе и экзаменатору, что ты освоил тему.
- Задача считается сданной в срок, если в ejudge (см. ниже) зафиксирована посылка решения, успешно принятого системой (результат OK) до наступления срока сдачи.
- Количество (точнее, процент от общего числа) домашних задач, сданных в срок, формируют оценку автоматом, которую можно исправить на экзамене (в обе стороны ☺).
Решения, скопированные друг у друга, считаются не сданными в срок.
Если решение не проходит проверку, придумайте побольше своих тестов. Напишите генератор входных данных (модуль random вам в помощь).
Домашняя работа — не олимпиада. Если что-то не получается, всегда можно спросить (FrBrGeorge, знакомого питониста).
Как сдавать домашнюю работу
TODO скопировать сюда скриншотики
Зарегистрироваться на факультетском Ejudge
- По этой же ссылке заполнить графу «Имя» (там должны быть имя и группа, кому оценку ставить)
ВНИМАНИЕ! Зарегистрированные пользователи заходят тут
- Выбрать 131-й «турнир» (UNИX Python 2019)
- Возможно, придётся пойти по ссылке «Confirm registration» («Подтвердить регистрацию»)
- Возможно, придётся пойти по ссылке «Participate» («Участвовать»)
- Выбрать соответствующую задачку
- Загрузить решение
- Прежде, чем загружать решение, убедитесь, что оно правильное. Не надо вместо этого делать много различных вариантов решения в надежде, что какой-то один всё-таки пройдёт тесты.
Если возникают вопросы — спрашивайте, для этого есть и интерфейс eJudge, и почта/ВК/телеграф/телефон (FrBrGeorge)
- Дождаться конца проверки (как правило, несколько секунд) и обновить страницу браузера
Как оформлять решение
Задача типа «написать программу»
По умолчанию, т. е. если иное не указано отдельно:
- программа читает со стандартного ввода и выводит на стандартный вывод
- вводимые данные корректны
- Тесты представляют собой наборы входных данных и соответствующие им наборы выходных. Если ваше решение останавливается с ошибкой, работает слишком долго или выдаёт не такие выходные данные, как в тесте, тест считается не пройденным.
⇒ Для ввода можно пользоваться input() (чаще даже eval(input())) без строки-подсказки, а для вывода — print(). Ещё раз: никаких переговоров с роботом — только ввод входных данных и вывод выходных, иначе программа не пройдёт тест!
Задача типа «написать функцию»
Решение — фрагмент программы, реализующий часть её функциональности (как правило — определение классов или функций), который ничего не вводит и не выводит сам.
Пример решения задачи: «Написать класс C, который ничего не делает»:
Тест — это также фрагмент программы, который использует определённые в решении объекты
- Пример теста:
- Пример теста:
К решению в конец приписывается тестирующий код
Полученная программа вводит и исполняет тест, вывод теста сравнивается с соответствующим эталоном
- Эталон для примера выше:
- Эталон для примера выше:
Тест может включать в себя проверку на то, что в классе нет полей, кроме тех, что указаны в условии, и вообще как-то исследовать ваш класс.
Пример решения задачи «написать функцию gt12(), которая принимает два заведомо сравнимых параметра и возвращает 1, если первый параметр больше второго, и 2 в противном случае»:
- Тест для этого решения:
- Ввод:
- Вывод:
2 2 1
Задача типа «написать модуль»
- Решение — программа-модуль, которую предполагается импортировать и использовать определённые в ней объекты (функции, классы и т. п.)
Решение может содержать раздел
- для самостоятельного запуска (при тестировании не используется)
Тесты представляют собой программы, которые импортируют модуль-решение под именем mod и задействуют определённые в нём объекты. Для каждой такой программы есть соответствующий файл с выходными данными, с которыми сравнивается результат её работы.
Тест может включать в себя проверку на то, что в модуле нет имён, кроме тех, что указаны в условии и разные другие проверки
Пример задачи: Написать модуль, в котором будет присутствовать целочисленный объект Count, изначально равный 0, и функция incr(level), увеличивающая Count на число level
Модуль-решение:
Тест:
Вывод:
0 100 Count incr
Сводный список домашних заданий
Прочитать и отщёлкать appetite.html, interpreter.html и introduction.html
- Добыть на рабочем компьютере
- Python3
- Редактор, в котором можно писать программы
- Написать и запустить программу из файла, в котором написано:
1 print("QQ")
Зарегистрироваться в EJudge (131 контест)
Ejudge (131-й турнир)
EJudge: HelloWorld 'Hello World'
Написать программу, которая выводит строку Hello, world (в точности)
(ввод не нужен)
Hello, world
Прочитать и прощёлкать учебник (до функций)
EJudge: IntPalindrome 'Число-палиндром'
Ввести целое положительное число и проверить, является ли оно палиндромом, т. е. совпадает ли первая цифра с последней, вторая — с предпоследней и т. д. Представлять число в виде последовательности (строки, списка и т. п.) нельзя. Вывести YES или NO соответственно. Лидирующие нули не учитывать (числа, заканчивающиеся на 0 — автоматически не палиндромы).
1234321
YES
EJudge: AnyPower 'Какая-нибудь степень'
Ввести небольшое натуральное число 2⩽N⩽1000000 и проверить, является ли оно степенью натурального числа (>1). Вывести YES или NO соответственно.
1024
YES
EJudge: BiSection 'Половинное деление'
Вводится строка — формула некоторой функции от x. В следующей строке вводятся через запятую два числа, A и B, такие что f(x) на [A,B] непрерывна, дифференцируема и имеет ровно один корень, будучи разных знаков на концах отрезка (проверять не надо). Найти и вывести этот корень с точностью 0.000001 (представление может быть любым). При вычислении f(x) (с помощью eval) предполагается, что в текущем пространстве имён присутствуют математические функции.
sin(x+0.00007) -1,2
-7.033348083496094e-05
( если перейти по ссылке «Вращающееся число», вы увидите некоторые подсказки)
EJudge: SwapFive 'Вращающееся число'
(Жак Арсак. Программирование игр и головоломок.) Для заданной цифры k найти такое минимальное целое неотрицательное число, оканчивающееся на k, что, умножая его на k, мы получим новое число, полученное из предыдущего вычеркиванием цифры k на конце и приписыванием ее в начале. Строки/кортежи и иные последовательности не использовать.
4
102564
Прочитать и прощёлкать тьюториал (и про цикл for)
EJudge: MaxSubsum 'Полоса удач'
Ввести в столбик последовательность целых (положительных и отрицательных) чисел, не равных нулю; в конце этой последовательности стоит 0. Вывести наибольшую сумму последовательно идущих элементов этой последовательности (не менее одного).
2 3 -7 -1 3 4 5 -2 -4 7 8 -6 -1 0
21
EJudge: PackedQueue 'Чудо-конвейер'
Ввести последовательность объектов Python (кортежей или целых чисел), и сымитировать работу Чудо-Конвейера. Если объект — кортеж, это означает, что на вход конвейеру подаются поочерёдно все объекты из этого кортежа. Если объект — натуральное число N, это означает, что с выхода конвейера надо снять поочерёдно N объектов, объединить их в кортеж и вывести. Если с конвейера нельзя снять N объектов, или в последовательности нет больше команд, Чудо-Конвейер немедленно останавливается.
("QWE",1.1,234),2,(None,7),0,2,(7,7,7),2,(12,),(),3,(5,6),3,100500
('QWE', 1.1) () (234, None) (7, 7) (7, 7, 12)
При подготовке последнего теста использовался графический редактор GIMP и формат XPM
EJudge: FindRect 'Морской бой'
Ввести несколько строк одинаковой длины, состоящих из символов '#' и '.'. Первый и последний символ каждой строки — '.', а первая и последняя строки состоят целиком из '-'. Известно (проверять не надо), что на получившемся поле изображены только прямоугольники, причём они не соприкасаются даже углами. Вывести количество этих прямоугольников.
------------ .###.....#.. .###.##..#.. .....##..... .....##..#.. ............ ............ .####..####. .......####. .......####. ------------
6
EJudge: SpiralDigits 'Цифры по спирали'
Ввести целые M и N, вывести последовательность 0 1 2 3 4 5 6 7 8 9 0 1 2 3 … в виде спирально (по часовой стрелке, из верхнего левого угла) заполненной таблицы N×M (N строк, M столбцов). Не забываем про то, что M и N могут быть чётными, нечётными и неизвестно, какое больше.
6,5
0 1 2 3 4 5 7 8 9 0 1 6 6 7 8 9 2 7 5 6 5 4 3 8 4 3 2 1 0 9
- Д/З мне: на следующий раз не забыть про множество
Прочитать в tutorial про функции, множества и различные последовательности
EJudge: AplusB2 'Простая функция'
Написать функцию (см. правила оформления таких Д/З), которая принимает два параметра, допускающие сложение, а результат сложения — умножение на целое число. Функция должна возвращать удвоенную сумму своих параметров.
print(AplusB2("A","B"))
ABAB
EJudge: MoarTuple 'Подсчёт кратных'
Написать функцию moar(a, b, n) от трёх параметров — целочисленных последовательностей a и b, и натурального числа n. Функция возвращает True, если в a больше чисел, кратных n, чем в b, и False в противном случае.
print(moar((25,0,-115,976,100500,7),(32,5,78,98,10,9,42),5))
True
EJudge: MaxFun 'Функция побольше'
Написать функцию maxfun(), которая принимает переменное число параметров — числовуюпоследовательность S, функцию F1 и, возможно, ещё несколько функций F2 … Fn. Возвращает она ту из функций Fi, сумма значений которой на всех элементах S наибольшая. Если таких функций больше одной, возвращается Fi с наибольшим i.
from math import * print(maxfun(range(-2,10), sin, cos, exp)(1))
2.718281828459045
EJudge: MumboJumbo 'Мумбо-Юмбо'
Ввод представляет собой строки из букв латинского алфавита. Это иероглифические письмена на языках двух племён: Mumbo и Jumbo. Чётные строки — предложения одного языка, нечётные — другого (какого — неизвестно). Иероглифы Mumbo и Jumbo частично одинаковые, а частично разные. Предложения на каждом языке в данном корпусе текстов содержат все разрешённые в этом языке иероглифы (т. е. если иероглиф разрешён в языке, он встречается хотя бы в одном предложении на этом языке). Если строка пустая, это признак окончания ввода. Известно, что в уникальном алфавите Mumbo иероглифов больше, чем в уникальном алфавите Jumbo. Определить и вывести, на каком языке написано первое предложение — Mumbo или Jumbo.
wazxwjd tvnhuj kjdjdsaxz kunvhts azkxdz vunshtk zzjdsxa nunvhct cdzxaa vtkuhvhnc dazx tunncvwh dzjasxz uunvhts dxdwzaxa vuhvuntt dzxad vthnwuh
Jumbo
TODO
Прочитать что Гвидо думает о хвостовых рекурсивных вызовах, про итераторы и генераторы, про yield from и про itertools
- (это не рекурсия, а вот итератор применить можно ☺)
EJudge: UniInterval 'Объединение отрезков'
Вводится кортеж пар натуральных чисел. Это координаты отрезков на прямой. Рассмотрим объединение этих отрезков и найдём длину этого объединения (т. е. совокупную длину всех «закрашенных» нашими отрезками отрезков на прямой).
(66, 91), (152, 230), (21, 81), (323, 342), (158, 211), (286, 332), (294, 330), (18, 58), (183, 236)
213
EJudge: BinPow 'Бинарное возведение в степень'
Написать рекурсивную функцию BinPow(), которая принимает три параметра: python3-объект a, натуральное число 0<N<1000000, и некоторую ассоциативную бинарную функциюf(). Функция BinPow() реализует алгоритм бинарного возведения в степень (кроме нулевой степени). Результатом BinPow(a, n, f) будет применение f(x) к a n-1 раз. Более точно, BinPow(a, 1, f) == a, BinPow(a, 2, f) == f(a,a), BinPow(a, 3, f) == f(a,f(a, a)) == f(f(a, a), a) (в силу ассоциативности), … BinPow(a, n, f) == f(f(…f(a, a), …), a).
print(BinPow(2,33,int.__mul__), 2**33) print(BinPow("Se", 7, str.__add__))
8589934592 8589934592 SeSeSeSeSeSeSe
EJudge: IterPi 'Пи /кродёться/'
Пользуясь формулой Лейбница для вычисления числа Пи:
написать бесконечный генератор pigen(), возвращающий последовательно 4, 4-4/3, 4-4/3+4/5, 4-4/3+4/5-4/7…;
P=pigen() print(next(P), next(P), next(P), next(P), sep="\n")
4.0 2.666666666666667 3.466666666666667 2.8952380952380956
EJudge: ChainSlice 'Режем лазанью'
Написать функцию chainslice(begin, end, seq0, seq1, …), которая принимает не менее трёх параметров: два целых числа и не менее одной последовательности. Рассмотрим последовательность seq, образованную всеми элементами seq0, затем — всеми элементами seq1, и т. д. Вернуть эта функция должна итератор, пробегающий элементы последовательности seq с №begin до №end-1 включительно.
print(*(chainslice(17, 33, range(7), range(8), range(6), range(9), range(5))))
2 3 4 5 0 1 2 3 4 5 6 7 8 0 1 2
Д/З мне:
I = iter(Seq) old = next(I) for new in I: ...
вместо
Прочитать и прощёлкать про строки в учебнике, в документации, а также про форматирование строк в учебнике и в документации.
Прочитать про bytes и bytearray в докумпентации
EJudge: TrimImage 'Обрезать картинку'
Вводятся строки, содержащие четыре целых числа и символ, разделённые пробелами. Код символа 32 < c < 128. Это абсцисса, ордината (ось ординат направлена вниз) некоторых точек, а также длина и ширина построенных на них прямоугольников, «нарисованных» с помощью указанных символов. Последняя строка начинается на четыре нуля (никаких трюков с -0 на этот раз ☺). Вывести наименьшую область, содержащюю все раскрашенные точки, нарисованные в порядке ввода прямоугольников. Область также прямоугольна и изначально заполнена символами '.'. Координаты и размеры могут быть отрицательны (в этом случае прямогуольник откладывается от исходной точки в противоположную сторону, а сама точка в него не попадает) или равны нулю.
1 2 10 10 * -2 -1 10 10 # 3 4 -10 10 @ 5 6 10 -10 % 0 0 0 0 0
............%%%%%%%%%% ............%%%%%%%%%% ............%%%%%%%%%% .....#######%%%%%%%%%% .....#######%%%%%%%%%% .....#######%%%%%%%%%% .....#######%%%%%%%%%% .....#######%%%%%%%%%% @@@@@@@@@@##%%%%%%%%%% @@@@@@@@@@##%%%%%%%%%% @@@@@@@@@@#####***.... @@@@@@@@@@#####***.... @@@@@@@@@@#####***.... @@@@@@@@@@********.... @@@@@@@@@@********.... @@@@@@@@@@********.... @@@@@@@@@@............ @@@@@@@@@@............
EJudge: MultTable 'Таблица умножения'
Ввести два натуральных числа через запятую: N и M. Вывести таблицу умножения от 1 до N включительно в формате, представленном ниже. Количество столбцов в выводе должно быть наибольшим, но общая ширина строки не должна превышать M (предполагается, что M достаточно велико, чтобы вместить один столбец). Ширина колонок под сомножители и произведения должна соответствовать максимальной ширине соответствующего значения (даже если в данной колонке данного столбца эта ширина не достигается, см. пример). Таким образом все столбцы должны быть одинаковой ширины, без учёта пробелов в конце строк, которых быть не должно. Разделители вида "===…===" должны быть ширины M.
11, 62
============================================================== 1 * 1 = 1 | 2 * 1 = 2 | 3 * 1 = 3 | 4 * 1 = 4 1 * 2 = 2 | 2 * 2 = 4 | 3 * 2 = 6 | 4 * 2 = 8 1 * 3 = 3 | 2 * 3 = 6 | 3 * 3 = 9 | 4 * 3 = 12 1 * 4 = 4 | 2 * 4 = 8 | 3 * 4 = 12 | 4 * 4 = 16 1 * 5 = 5 | 2 * 5 = 10 | 3 * 5 = 15 | 4 * 5 = 20 1 * 6 = 6 | 2 * 6 = 12 | 3 * 6 = 18 | 4 * 6 = 24 1 * 7 = 7 | 2 * 7 = 14 | 3 * 7 = 21 | 4 * 7 = 28 1 * 8 = 8 | 2 * 8 = 16 | 3 * 8 = 24 | 4 * 8 = 32 1 * 9 = 9 | 2 * 9 = 18 | 3 * 9 = 27 | 4 * 9 = 36 1 * 10 = 10 | 2 * 10 = 20 | 3 * 10 = 30 | 4 * 10 = 40 1 * 11 = 11 | 2 * 11 = 22 | 3 * 11 = 33 | 4 * 11 = 44 ============================================================== 5 * 1 = 5 | 6 * 1 = 6 | 7 * 1 = 7 | 8 * 1 = 8 5 * 2 = 10 | 6 * 2 = 12 | 7 * 2 = 14 | 8 * 2 = 16 5 * 3 = 15 | 6 * 3 = 18 | 7 * 3 = 21 | 8 * 3 = 24 5 * 4 = 20 | 6 * 4 = 24 | 7 * 4 = 28 | 8 * 4 = 32 5 * 5 = 25 | 6 * 5 = 30 | 7 * 5 = 35 | 8 * 5 = 40 5 * 6 = 30 | 6 * 6 = 36 | 7 * 6 = 42 | 8 * 6 = 48 5 * 7 = 35 | 6 * 7 = 42 | 7 * 7 = 49 | 8 * 7 = 56 5 * 8 = 40 | 6 * 8 = 48 | 7 * 8 = 56 | 8 * 8 = 64 5 * 9 = 45 | 6 * 9 = 54 | 7 * 9 = 63 | 8 * 9 = 72 5 * 10 = 50 | 6 * 10 = 60 | 7 * 10 = 70 | 8 * 10 = 80 5 * 11 = 55 | 6 * 11 = 66 | 7 * 11 = 77 | 8 * 11 = 88 ============================================================== 9 * 1 = 9 | 10 * 1 = 10 | 11 * 1 = 11 9 * 2 = 18 | 10 * 2 = 20 | 11 * 2 = 22 9 * 3 = 27 | 10 * 3 = 30 | 11 * 3 = 33 9 * 4 = 36 | 10 * 4 = 40 | 11 * 4 = 44 9 * 5 = 45 | 10 * 5 = 50 | 11 * 5 = 55 9 * 6 = 54 | 10 * 6 = 60 | 11 * 6 = 66 9 * 7 = 63 | 10 * 7 = 70 | 11 * 7 = 77 9 * 8 = 72 | 10 * 8 = 80 | 11 * 8 = 88 9 * 9 = 81 | 10 * 9 = 90 | 11 * 9 = 99 9 * 10 = 90 | 10 * 10 = 100 | 11 * 10 = 110 9 * 11 = 99 | 10 * 11 = 110 | 11 * 11 = 121 ==============================================================
EJudge: PatternFind 'Простой шаблон'
Ввести строку, содержащую произвольные символы (кроме символа «@»). Затем ввести строку-шаблон, которая может содержать символы '@'. Проверить, содержится ли в исходной строке подстрока, совпадающая со строкой-шаблоном везде, кроме символов '@'; на месте '@' в исходной строке должен стоять ровно один произвольный символ. Вывести наименьшую позицию в строке, с которой начинается эта подстрока, или '-1', если её там нет. Использовать регулярные выражения нельзя! ☺
lorem ipsum, quia dolor sit, amet, consectetur dolor @it,@@met
18
Прочитать про словари в учебнике и в документации
EJudge: DungeonMap 'Карта подземелья'
Вводится карта проходимых в обе стороны тоннелей подземлья в виде строк, содержащих разделённые пробелом названия двух пещер, которые соединяет соответствующий тоннель. Две последние строки не содержат пробелов — это название входа в подземелье и название выхода. Вывести "YES", если из входа можно попасть в выход, и "NO" в противном случае. Пары могут повторяться или содержать одинаковые слова.
markers jumping jumping guinea skiing pre markers gauge skiing mpeg solar jackson skiing solar guinea gauge mpeg honor pre honor guinea gauge pre mpeg markers guinea markers gauge honor mpeg markers jumping skiing jumping
NO
генератор тестовых даных (вам понадобится google-10000-english.txt)
EJudge: FarGalaxy 'В далёкой галактике'
Ввести построчно четвёрки вида «число число число слово», где первые три числа — это координаты галактики по имени «слово» (некоторые галактики могут называться одинаково, но координаты у всех разные). Последняя строка ввода не содержит пробелов и не учитывается. Вывести в алфавитном порядке имена любых двух наиболее удалённых друг от друга галактик.
35.764 -797.636 -770.320 almost 88.213 -61.688 778.457 gene -322.270 -248.555 -812.730 trend 721.262 630.355 968.287 dow -895.519 -970.173 97.282 non -561.036 -350.840 -723.149 disco -151.546 -900.962 -658.862 bidder -716.197 478.576 -695.843 hawaii -744.664 -173.034 -11.211 sad -999.968 990.467 650.551 erik .
almost erik
генератор тестовых даных (вам понадобится google-10000-english.txt)
EJudge: CheckHash 'Хороший ли хеш'
Написать функцию checkhash(seq, f, mod), которой на вход подаётся последовательность неравных друг другу (это гарантируется) хешируемых объектов, хеш-функция и число mod. Функция формирует новую редуцированную хеш-функцию r()=f()%mod, и собирает статистику коллизий по каждому значению r() на исходной последовательности. checkhash(seq, f, mod) возвращает кортеж из двух элементов — наибольшее и наименьшее количество произошедших коллизий.
from math import * print(checkhash(range(-1000000,1000000,77),hash,128)) print(checkhash(range(-1000000,1000000,77),lambda x: int(f"{sin(x+1):14.13f}"[-5:]),128))
(204, 202) (260, 112)
В примере используется питоновская функция hash(), котороая, как мы выяснили, при каджом новом запуске может возвращать иные значения. В тестах её нет.
- В примере используется формула из лекции. Что-то с ней явно не так!
- Прочитать про все эти удивительные вещи по ссылкам и прощёлкать примеры оттуда
Замыкания: Gabor Laszlo Hajba и Dmitry Soshnikov
Декораторы хабр и learnpython
Параметрические декораторы хабр
TODO
EJudge: SimpleDecorator 'Простой декоратор'
Написать функцию-декоратор nonify(func), которая заменяет возвращаемое значение функции func на None, если оно было пустое (и не меняет в противном случае).
@nonify def aNb(a, n, b): return a*n+b print(aNb(1,2,3), aNb("QWE",0,""))
5 None
EJudge: FixFloat 'Фиксированная точность'
Написать функцию-параметрический декоратор fix(n), с помощью которой все вещественные (как позиционные, так и именные) параметры произвольной декорируемой функции, а также её возвращаемое значение, округляются до n-го знака после запятой. Если какие-то параметры функции оказались не вещественными, или не вещественно возвращаемое значение, эти объекты не меняются.
@fix(4) def aver(*args, sign=1): return sum(args)*sign print(aver(2.45675901, 3.22656321, 3.432654345, 4.075463224, sign=-1))
-13.1916
EJudge: VirtualTurtle 'Примитивная черепашка'
Написать параметрический генератор turtle(coord, direction), описывающий движение «черепахи» по координатной плоскости. coord — это кортеж из двух целочисленных начальных координат, direction описывает первоначальное направление (0 — восток, 1 — север, 2 — запад, 3 — юг). Координаты увеличиваются на северо-восток. Генератор принимает три команды — "f" (переход на 1 шаг вперёд), "l" (поворот против часовой стрелки на 90°) и "r" (поворот по часовой стрелке на 90°) и возвращает текущие координаты черепахи.
1 0 1 0 1 1 1 1 2 1 3 1 3 1 3 0 3 -1 3 -1
Исследовательская задача.
EJudge: StatCounter 'Статистика вызовов'
Написать, держитесь крепче, генератор-декоратор statcounter(), который конструирует объекты (назовём один из них stat) со следующим поведением. Первый вызов next(stat) (он же stat.send(None)) возвращает словарь, в котором stat будет хранить информацию вида функция: количество вызовов, где функция — это исходный (не обёрнутый) объект-функция (да, так тоже можно!). Все последующие вызовы stat.send(function) оборачивают вызов произвольной функции function увеличением на 1 соответствующего элемента словаря. Глобальными именами пользоваться нельзя. В примере видны уникальные id объектов, в тестах их не будет (я воспользуюсь function.__name__ или просто не буду их учитывать).
stat = statcounter() stats = next(stat) @stat.send def f1(a): return a+1 @stat.send def f2(a, b): return f1(a)+f1(b) print(f1(f2(2,3)+f2(5,6))) print(stats)
21 {<function f2 at 0x7fc3151ebb90>: 2, <function f1 at 0x7fc315283e60>: 5}
- Прочитать
про модули и пакеты в учебнике
про классы в учебнике и тут: FrBrGeorge/ClassesInPython3
В задачах типа «написать модуль» требуется написать модуль (с любым именем, в тест он приедет с именем mod).
EJudge: FakeRnd 'Неслучайные числа'
Написать модуль, в котором будет две фальшивые функции: randrange() и randint(), которые принимают тек же параметры, что и настоящие. При каждом чётном по порядку вызове функция randint(a, b) возвращает a, при нечётном — b. Функция randrange() может принимать от 1 до 4 параметров. Четвёртый параметр она игнорирует, а начало диапазона a, конец диапазона b и шаг d интерпретирует так. Если при очередном вызове эти величины совпадают с предыдущим вызовом, то randrange() сперва работает как если бы возвращала очередной элемент range(), то есть сначала a, затем a+d и т. д., пока не доберётся до конца диапазона, после чего продолжает с начала диапазона (шаг при этом не сбивается, см. пример). Пустых диапазонов (когда знак шага не соответствует концам диапазона) во входных данных нет. Если же при очередном вызове значения a, b или d оказываются иными, процесс запускается с начала.
print(*(mod.randrange(5) for i in range(6))) print(*(mod.randrange(10,15,2) for i in range(7))) print(*(mod.randrange(20,36,3,False) for i in range(9))) print(*(mod.randint(5,7) for i in range(3)), *(mod.randint(5,17) for i in range(5)))
0 1 2 3 4 0 10 12 14 11 13 10 12 20 23 26 29 32 35 22 25 28 5 7 5 17 5 17 5 17
EJudge: CountFields 'Счётчик полей'
Написать функцию fcounter(), которая первым параметром получает некоторый класс, а остальные параметры применяет для создания экземпляра этого класса. Функция должна возвращать 4 отсортированных списка: имена методов класса, имена полей класса, имена методов, которые появились в экземпляре и имена полей, которые появились в экземпляре (под «полями» имеются в виду не-callable() объекты).
class C: x, y, z = 1, 3, 5 def X(self): return self.x def Y(self): return self.y def __init__(self, dx, dy, dz): self.x = dx self.Y = dy self.Z = dz cm, cf, om, of = fcounter(C, 6, 7, 8) print("Class: methods", *cm) print("Class: fields", *cf) print("Object: methods", *om) print("Object: fields", *of)
Class: methods X Y Class: fields x y z Object: methods Object: fields Y Z
TODO
EJudge: BitCoding 'Сжатие со словарём'
Написать модуль, в котором будет 4 функции. Первые две: shex(n), которая переводит число n в 64-ричное представление, и xehs(s), которая переводит строку с 64-ричным числом в число. 64-ричная система счисления пользуется «цифрами» с ASCII-кодом от 32 до 32+63=95 (т. е. от пробела до подчёркивания) включительно. Функция encode(txt) упаковывает строку txt, состоящую из символов диапазона " "…"_" по следующим правилам. Символы, встретившиеся в тексте, упорядочиваются по убыванию частоты их появления в тексте (вторичный ключ — сам символ). Самому частому (и с наибольшим ASCII-кодом, если таковых несколько) ставится в соответствие бит "0", следующему — последовательность битов "10", следующему — "110", и т. д. Биты записываются единой строкой, строка дополняется нулями, если это необходимо, и превращается в 64-ричное число. Функция encode(txt) возвращает кортеж (длина txt, строка упорядоченных символов, закодированная строка). Четвёртая функция, decode(length, chars, code), раскодирует строку code, используя описанное выше сопоставление chars битам, и возвращает раскодированную строку длиной length.
print(xehs("BREAKFAST")) print(shex(10844745761445995)) res = encode("ENGINEERING WITHOUT MANAGEMENT IS ART.") print(res) txt = decode(*res) print(txt)
9792630319357172 FASTBREAK (38, 'NETI GARMWUSOH.', 'GW*_N?>_[M__?_O_;W^_/WU_IO=_][]_;__ ') ENGINEERING WITHOUT MANAGEMENT IS ART.
Прочитать про классы в tutorial; про «волшебные методы» например, тут
Прочитать про ограничения на перегрузку спецметодов в справочнике
EJudge: DahDit 'Морзянка'
Написать класс morse("строка"), экземпляр которого переводит арифметические выражения в морзянку! Параметр «строка» бывает разных видов, более подробно описан в подсказках, желающие могут догадаться о его компонентах по примеру (пример почти полный). «+» — точка, «-» — тире, «~» — промежуток между буквами (бывает только между буквами и только один, проверять не надо).
1 print(-+morse()) 2 print(-++~+-+morse()) 3 print(--+~-~-++~+++-morse()) 4 print(--+~-~-++~+++-morse(".-")) 5 print(--+~-~-++~+++-morse("..-")) 6 print(--+~-~-++~+++-morse("..-|")) 7 print(--+~-~-++~+++-morse("dot DOT dash")) 8 print(--+~-~-++~+++-morse("ai aui oi ")) 9 print(--+~-~-++~+++-morse("dot dot dash ///"))
dah dit. dah di dit, di dah dit. dah dah dit, dah, dah di dit, di di di dah. --. - -.. ...- --. - -.. ...- --. - -.. ...-| dash dash DOT, dash, dash dot DOT, dot dot dot dash. oi oi aui, oi, oi ai aui, ai ai ai oi dash dash dot, dash, dash dot dot, dot dot dot dash///
EJudge: CyberSausage 'Киберколбаса'
Написать класс sausage, имитирующий киберколбасу. Киберколбаса может быть проинициализирована нулём значений (создаётся колбаса по умолчанию), одним (фарш) и двумя (фарш и объём). Длина целого батона киберколбасы 12 символов фарша и 2 оболочки. Колбаса единичного объёма — это один полный батон, более, чем единичного — это несколько батонов (последний, возможно, неполон). Неполный батон заканчивается срезом. Киберколбаса поддерживает операции умножения и деления на целое число, а также сложения и вычитания с другой киберколбасой (фарш результата совпадает с фаршем первого операнда). Если объём киберколбасы нулевой, батон считается пустым.
/------------\ |pork!pork!po| |pork!pork!po| |pork!pork!po| \------------/ /----------| |HAMHAMHAMH| |HAMHAMHAMH| |HAMHAMHAMH| \----------| /------------\/---| |SPAM.SPAM.SP||SPA| |SPAM.SPAM.SP||SPA| |SPAM.SPAM.SP||SPA| \------------/\---| /------------\/------------\/------------\/-| |pork!pork!po||pork!pork!po||pork!pork!po||p| |pork!pork!po||pork!pork!po||pork!pork!po||p| |pork!pork!po||pork!pork!po||pork!pork!po||p| \------------/\------------/\------------/\-| /------------\/--------| |HAMHAMHAMHAM||HAMHAMHA| |HAMHAMHAMHAM||HAMHAMHA| |HAMHAMHAMHAM||HAMHAMHA| \------------/\--------| /------------\ |SPAM.SPAM.SP| |SPAM.SPAM.SP| |SPAM.SPAM.SP| \------------/ /| || || || \| True /| || || || \| True
EJudge: SelfCount 'Сколько экземпляров'
Написать класс WeAre, объекты которого содержат поле count, содержащее количество существующих экземпляров этого класса. Игнорировать попытки изменить значение этого поля вручную или удалить его.
1 3 3 3 2
Почитать ещё о классах и наследовании в учебнике
EJudge: UniSize 'Размер объекта'
Написать декоратор класса sizer, который добавляет в него поле size, равное длине объекта, если у объекта есть длина, или модулю целочисленного представления объекта в противном случае (предполагается, что ошибок нет). Предоставить пользователю возможность произвольно менять это поле.
QSXWDC 2.718281828459045 6 2 Wait what?
Исследовательская задача. Результаты моего исследования в комментариях по ссылке (нажать «комментарии»).
EJudge: DivStr 'Делимая строка'
Написать класс DivStr(str), полностью (за исключением правых операций со строками и split()/splitlines()) воспроизводящий работу str. Дополнительно класс должен поддерживать операцию деления «/n», где n — натуральное число, которая должна возвращать n-ю часть от начала строки (если не делится, округлённую в меньшую сторону, если n>len(s) — пустую строку). Задача в том, чтобы любое возвращаемое методами значение типа str превращалось в DivStr. Согласно документации, мы не можем подсунуть методы, начинающиеся на «__», прямо в __dict__, или поймать __getattr__-ом, или даже __getattribute__-ом, а должны задать их явно, например, с помощью def. С другой стороны, руками все методы перебивать не хочется. См. далее.
s = DivStr("Qwertupy") print(len(s)) print(s*3/2) print((s+"ZZZZZZZZZZ")/2) print(s[3:]/2) print(s[0].join("12345678")/2)
8 QwertupyQwer QwertupyZ rt 1Q2Q3Q4
EJudge: LetterAttr 'Буквенное поле'
Написать класс LetterAttr, в котором будут допустимы поля с любым именем; значение каждого поля по умолчанию будет совпадать с именем поля (строка), а при задании нового строкового значения туда будут попадать только буквы, встречающиеся в имени поля.
letter digit teller rteteller
Прочитать про исключения в учебнике и в справочнике про исключения, try и raise
EJudge: BoldCalc 'Надёжный калькулятор'
Написать программу — калькулятор с переменными и обработкой ошибок
- Команда, начинающаяся на '#' — комментарий
Команда вида Переменная=выражение задаёт переменную
Команда вида выражение выводит значение выражения.
- Если команда содержит знак "=", но не является присваиванием, выводится диагностика "invalid assignment" (см. пример)
- Если слева от "=" находится не идентификатор, выводится диагностика "invalid identifier (см. пример)"
- В случае любых других ошибок выводится текст ошибки.
«Выражение» — это произвольное выражение Python3, в котором вдобавок можно использовать уже определённые переменные (и только их). Пробелов в командах нет. Пустая команда или точка означает конец вычислений. Калькулятор вводит и исполняет команды по одной, тут же выводя диагностику, но в тестах это выглядит как ввод последовательности строк и вывод последовательности строк.
42 100500//33 "Qq!"*(6-2) # Здесь ошибка 3,,5 10/(8-8) "wer"[2]+"qwe"[1] "wer"[7]+"qwe"[9] 1+(2+(3 a0=5 b0=7 # И здесь ошибка 12N=12 # И ещё где-то были a0+b0*8 c=b0//2+a0 d==100 c+d sorted(dir()) .
42 3045 Qq!Qq!Qq!Qq! invalid syntax (<string>, line 1) division by zero rw string index out of range unexpected EOF while parsing (<string>, line 1) invalid identifier '12N' 61 invalid assignment 'd==100' name 'd' is not defined ['__builtins__', 'a0', 'b0', 'c']
Include: Ничего не найдено по регулярному выражению «== Д/З ==$».
Рекомендации по дальнейшему изучению
Долги: б/м удобное программирование на Python.
sys — сам Python
.argv (BTW, optparse
.path
.ps1/.ps2
.stdin/.stdout/.stderr
.version/.platform./.
- …
os — операционая система
.environ
- работа с каталогами/файлами/процессами/... — чем не системное программирование?
.path. — с именами файлов
.getrandom/.urandom
randrange/randint, random и пр.
choice/random.sample("QWRTRUYOIUIOOPDSFGHFDH",3)
shuffle
seed и пр.
среди прочего (3.6+): random.choices("ABC",(1,2,4),k=10)
Что пропустили
- Асинхронные свойства
array (⇒ https://numpy.org и т. д.)
… тысячи их
- venv/pip и прочая разработка
BTW: https://pypi.org : 210,100 projects