Працюємо з тим самим кошиком покупок, що в лекції й практиці:
покупки = ["хліб", "молоко", "яблука", "мед", "сіль"]
ціни = {"хліб": 28.5, "молоко": 32.0, "яблука": 19.9, "мед": 145.0, "сіль": 12.0}
кількості = [2, 1, 3, 1, 1]
Правило на все ДЗ: розрахункові функції нічого не друкують. Друкує той, хто їх
викликав. Кожен рівень закінчується блоком assert — якщо він мовчить, рівень зданий.
рівень 1Рівень 1 — База
Напиши три маленькі функції, у кожної з яких є return і докстрінг з одного речення.
вартість_доставки(сума)— повертає число:79, якщо сума чека менша за 200;49, якщо від 200 до 499.99;0, якщо 500 і більше. Напиши це кількомаreturnбез жодногоelse.середня_ціна(ціни)— повертає середню ціну зі словника цін, округлену до двох знаків.назви_дорожче(ціни, межа)— повертає список назв, чия ціна більша за межу.
Перевір себе:
assert вартість_доставки(0) == 79
assert вартість_доставки(199.99) == 79
assert вартість_доставки(200) == 49
assert вартість_доставки(499.99) == 49
assert вартість_доставки(500) == 0
assert середня_ціна(ціни) == 47.48
assert назви_дорожче(ціни, 100) == ["мед"]
assert назви_дорожче(ціни, 1000) == []
print("✅ рівень 1")
Зроблено, якщо: усі вісім assert мовчать, у вартість_доставки немає слова
else, і help(вартість_доставки) показує твій докстрінг.
рівень 2Рівень 2 — Плюс
Візьми будь-який свій попередній скрипт на 15-30 рядків (згодиться домашка з теми 12) і розріж його на функції. Умови:
- Кожна функція робить одну річ — в описі того, що вона робить, не має бути «і».
- Жодна розрахункова функція не містить
print. Друк — окремою функцією. - У кожної функції є докстрінг: що повертає і що означають параметри.
- Головний сценарій після рефакторингу — це послідовність викликів, а не суцільний потік обчислень.
Потім доведи, що розрахунок не зіпсувався. Збережи результат старого скрипта в імʼя й порівняй його з тим, що дають нові функції:
assert новий_результат == старий_результат, "рефакторинг змінив відповідь!"
assert друкувальна_функція(...) is None, "функція, яка тільки друкує, повертає None"
print("✅ рівень 2")
Наостанок напиши в комірці markdown два речення: скільки місць довелось би правити в старій версії при зміні однієї формули — і скільки в новій.
Зроблено, якщо: обидва assert мовчать, у файлі є щонайменше три функції з
докстрінгами, жодна розрахункова не містить print, і два речення про місця правки
написані.
рівень 3Рівень 3 — Виклик
Напиши функцію звіт_кошика(ціни, покупки, кількості), яка повертає кортеж
з чотирьох значень: (сума, ставка_знижки, до_сплати, найдорожча_назва).
Умови:
- Рання відмова першим рядком тіла. Якщо кошик порожній — одразу
return (0, 0.0, 0, None), без жодного вкладеногоif. - Функція чиста: не друкує, не змінює передані списки й словник, на однакових аргументах завжди дає однакове.
- Усередині вона викликає інші функції — щонайменше
ставка_знижки(сума)з практики. Порахувати все в одному тілі не можна. - Докстрінг описує, що саме лежить у кожному з чотирьох елементів кортежу.
Перевірка:
сума, ставка, разом, найдорожча = звіт_кошика(ціни, покупки, кількості)
assert (сума, ставка, разом, найдорожча) == (305.7, 0.05, 290.41, "мед")
assert звіт_кошика(ціни, [], []) == (0, 0.0, 0, None)
assert звіт_кошика(ціни, ["сіль"], [1]) == (12.0, 0.0, 12.0, "сіль")
assert покупки == ["хліб", "молоко", "яблука", "мед", "сіль"], "вхідні дані змінились"
assert звіт_кошика(ціни, покупки, кількості) == звіт_кошика(ціни, покупки, кількості)
print("✅ рівень 3")
Зроблено, якщо: усі пʼять assert мовчать, перший рядок тіла — рання відмова
з return, у тілі є виклик хоча б однієї іншої функції, і help(звіт_кошика)
пояснює всі чотири елементи кортежу.
Підказки
- Не знаєш,
returnчиprint? Спитай себе: «чи знадобиться це число комусь далі в програмі?». Якщо так —return. Функція завжди може віддати число, а надрукувати його можна зовні; навпаки не працює. - Кілька
return— це нормально. Якщо хочеться написатиelse, спробуй спершу перевернути умову й вийти одразу:if not кошик: return …. Часто після цьогоelseстає непотрібним. - Кома в
returnстворює кортеж.return сума, ставка— це вже пара, дужки ставити не обовʼязково. На боці виклику її розпакуєсума, ставка = функція(...)з теми 07. - Порожній кошик — не дрібниця. Перевір усі свої функції на
[]і{}окремо: саме там ховаються ділення на нуль іmax()на порожній послідовності. - Якщо
assertпадає з незрозумілим повідомленням, надрукуй те, що функція насправді повернула, поруч із тим, що очікувалось. Половина розбіжностей — цеNoneзамість числа, тобто забутийreturn.