Python: задачки и вопросы
6.99K subscribers
1.35K photos
1 video
1 file
134 links
Вопросы и задачки для подготовки к собеседованиям и прокачки навыков

Разместить рекламу: @tproger_sales_bot

Правила общения: https://tprg.ru/rules

Другие каналы: @tproger_channels

Другие наши проекты: https://tprg.ru/media
Download Telegram
Please open Telegram to view this post
VIEW IN TELEGRAM
1
Python: задачки и вопросы
Развёрнутое пояснение:

1. Вызов save(5) создаёт пустой список result.

2. В try-блоке вычисляется value // 2, то есть 2, и это значение добавляется в result.

3. Достигается инструкция return result.

4. Перед фактическим возвратом управление обязательно переходит в finally-блок, так как finally выполняется при любом выходе из try/except.

5. В finally вычисляется value * 2, то есть 10, и это значение тоже добавляется в тот же список result.

6. Теперь result содержит [2, 10].

7. Функция возвращает ссылку на этот список.

8. print выводит [2, 10].

Почему это важно: в реальном коде finally используется для cleanup, метрик или освобождения ресурсов. Если при этом мутировать объект, который планируется вернуть из функции, финальное значение изменится ещё до передачи вызывающей стороне. Это стреляет в сценариях, когда return и cleanup работают с одной структурой данных, например при сборке ответа, логировании или обновлении кэша.
2
Please open Telegram to view this post
VIEW IN TELEGRAM
2
Python: задачки и вопросы
Развёрнутое пояснение:

1. Цикл for n in 'ba' регистрирует колбэки в порядке 'b', затем 'a'.

2. Вызов stack.close() запускает колбэки в обратном порядке: сначала 'a', потом 'b'.

3. Колбэк 'a' печатает a и выбрасывает RuntimeError('a'), но ExitStack ловит это исключение и продолжает выполнение оставшихся колбэков.

4. Колбэк 'b' печатает b и выбрасывает RuntimeError('b'); ExitStack запоминает уже это последнее исключение.

5. После завершения всех колбэков ExitStack поднимает сохранённое исключение, которое ловит внешний except и печатает caught b. Итоговый вывод: a, b, caught b.

Почему это важно: в реальных сервисах cleanup-колбэки закрывают соединения с базой, временные файлы или снимают блокировки. Порядок закрытия обратен порядку регистрации, при этом один упавший колбэк не должен прервать остальные освобождения ресурсов, иначе останутся висячие соединения или утечки.
1
Please open Telegram to view this post
VIEW IN TELEGRAM
2
Python: задачки и вопросы
Развёрнутое пояснение:

1. Создаётся словарь base с ключом retry, значением которого является другой словарь {limit: 3}.

2. copy.copy(base) создаёт новый внешний словарь cfg, но значение по ключу retry — это тот же вложенный словарь, а не его отдельная копия.

3. Через cfg['retry']['limit'] = 5 изменяется значение во вложенном словаре, на который ссылаются и base, и cfg.

4. Поэтому base['retry']['limit'] теперь равно 5, и print выводит 5.

Почему это важно: в реальных проектах часто клонируют конфиг, кэш или настройки. Если использовать поверхностное копирование, вложенные изменяемые структуры остаются общими, и правки в одной копии неожиданно затрагивают другую. Для полной изоляции вложенных объектов нужен copy.deepcopy.
2
Please open Telegram to view this post
VIEW IN TELEGRAM
2
Развёрнутое пояснение

a * b умножает векторы поэлементно: первый элемент с первым, второй со вторым, третий с третьим. Результат — массив [4 10 18]. a @ b делает те же умножения и складывает их в одно число: 4 + 10 + 18 = 32. Это скалярное произведение, на нём построены линейная регрессия и косинусное сходство текстов.

Если перепутать операторы, код не упадёт: обе операции корректны для векторов одинаковой длины. Ошибка проявится только неправильными числами в результате, и заметить её можно только по смыслу этих чисел.

Почему это важно

Задача проверяет, различаете ли вы две операции по смыслу: где нужно перемножить признаки поэлементно, а где — свернуть векторы в одно число.

💻 Если знаете Python, а с математикой за NumPy знакомы хуже — посмотрите курс «Математика для анализа данных» Практикума PRO. Скалярное произведение, нормы и работа с векторами в NumPy — это модуль линейной алгебры, дальше матанализ до градиентного спуска, теорвер и статистика до A/B-тестов. 1000+ задач, практика на Python в тренажёре, в конце — симулятор математической секции собеседования.

Реклама. Рекламодатель: АНО ДПО "Образовательные технологии Яндекса" ИНН 7704282033, erid: 2W5zFFzVHzh
Please open Telegram to view this post
VIEW IN TELEGRAM
2
Первый модуль курса «Алгоритмы и структуры данных» в Практикуме PRO открыт бесплатно: 10 тем, около 7 часов.

Внутри — понятие алгоритма, метод скользящего среднего и метод двух указателей, пробные задачи с проверкой. Хватает, чтобы ещё до оплаты понять, нужен ли вам курс целиком.

Дальше в программе: оценка сложности, структуры данных, сортировки, хеш-таблицы, деревья, графы и динамическое программирование. 100+ задач, код-ревью от практикующих разработчиков и пробное алгоритмическое собеседование. Курс идёт 4 месяца при нагрузке около 10 часов в неделю.

💻 Открыть бесплатный модуль: https://tprg.ru/n6Cr

Реклама. Рекламодатель: АНО ДПО "Образовательные технологии Яндекса" ИНН 7704282033, erid: 2W5zFKAB2eV
Please open Telegram to view this post
VIEW IN TELEGRAM
3
Please open Telegram to view this post
VIEW IN TELEGRAM
Python: задачки и вопросы
Развёрнутое пояснение:

1. Импортируется Counter из collections.

2. a получает значения x=2, y=1; b получает x=1, y=2.

3. Операция a - b вычитает счётчики по каждому ключу: x становится 2 - 1 = 1, y становится 1 - 2 = -1.

4. Counter автоматически отбрасывает ключи с неположительным значением, поэтому результат содержит только x=1.

5. Метод elements() возвращает итератор, который выдаёт каждый ключ столько раз, чему равен его положительный счётчик: здесь 'x' один раз.

6. list(...) превращает итератор в список ['x'], который и печатает print.

Почему это важно: при сравнении частот событий, тегов или ошибок за два периода часто используют вычитание Counter. Важно помнить, что отрицательные и нулевые значения исчезают из результата, а elements() не покажет отсутствующие ключи, иначе можно принять просевшие метрики за новые события.
2
Please open Telegram to view this post
VIEW IN TELEGRAM
2
Python: задачки и вопросы
Развёрнутое пояснение:

Ключ сортировки — второе число пары, поэтому ('b', 1) и ('d', 1) для сортировки равны. Python гарантирует стабильность: равные по ключу элементы сохраняют исходный порядок. 'b' стояла раньше 'd', 'a' раньше 'c' — ответ A.

Гарантия прописана в документации. Ошибаются здесь обычно те, кто привык к C++, где std::sort стабильность не обещает и для неё существует отдельный std::stable_sort.
Практическое следствие: сортировка по нескольким критериям делается последовательными проходами от младшего ключа к старшему, без составных кортежей.

Почему это важно

Задача выглядит как вопрос про синтаксис, но отвечает на неё знание алгоритма: какие гарантии даёт сортировка, почему, чем это отличается в других языках.

💻 Если хочется разобраться, как устроены сортировки, — посмотрите курс «Алгоритмы и структуры данных» Практикума PRO, там под них отведён отдельный модуль. Решения проходят автопроверку в Яндекс Контесте с ограничениями по времени и памяти, финальные задачи смотрит ревьюер и требует обосновать сложность, в конце — пробное алгоритмическое собеседование с наставником.

Реклама. Рекламодатель: АНО ДПО "Образовательные технологии Яндекса" ИНН 7704282033, erid: 2W5zFK4PUL9
Please open Telegram to view this post
VIEW IN TELEGRAM
3
Please open Telegram to view this post
VIEW IN TELEGRAM
1
Python: задачки и вопросы
Развёрнутое пояснение:

1. Цикл for event_type in ('click', 'scroll') начинает первую итерацию: event_type = 'click'.

2. На этой итерации определяется функция handler(e=event_type). Значение по умолчанию для e вычисляется сейчас и сохраняется как 'click' внутри объекта функции.

3. Переменная event_type в теле handler не является локальной: она свободная и будет искаться в объемлющей области видимости во время вызова.

4. Вторая итерация: event_type = 'scroll'. Определяется новая функция handler, её значение по умолчанию для e — 'scroll'.

5. После цикла event_type остаётся равной 'scroll', так как это последнее значение итерируемого.

6. Вызов handlers[0]() использует значение по умолчанию e='click' и берёт event_type='scroll' из замыкания, возвращая ('click', 'scroll').

7. Вызов handlers[1]() использует e='scroll' и event_type='scroll', возвращая ('scroll', 'scroll').

Почему это важно: разница между ранним и поздним связыванием встречается при создании колбэков, обработчиков событий и фабрик функций в цикле. Ошибка приводит к тому, что все созданные обработчики ссылаются на последнее значение переменной цикла, а использование параметра по умолчанию — распространённый способ зафиксировать нужное значение для каждой функции.
1
Плохо помните математику и боитесь её, но она нужна для работы? Присмотритесь к курсу «Математика для анализа данных» от Практикума PRO.

В рамках курса вы решите 100+ практических задач и подготовитесь к математической части собеседований аналитиков и специалистов по data science. А для этого погрузитесь в четыре раздела математики:

1. Линейная алгебра: векторы, матрицы, скалярное произведение, нормы, определители, смена базиса.

Зачем. Работа с данными держится на линейной алгебре. Вектор — это просто строка с характеристиками объекта (например, клиент с параметрами: возраст, доход, количество покупок). Матрица — это вся таблица с данными. Линейная алгебра учит превращать текст или картинки в наборы чисел и вычислять, насколько объекты похожи друг на друга (например, для рекомендательных систем или поисковиков).


2. Функции: линейные и полиномиальные, логарифмы, модули, композиции функций, графики.

Зачем. Показывает, как описывать реальные процессы формулами. Например, как цена квартиры зависит от её площади или как меняется спрос на товар. Логарифмы позволяют работать с огромными разбросами значений (когда у одного пользователя 2 подписчика, а у другого — 10 миллионов), приводя их к удобному масштабу.


3. Матанализ: пределы, производные, интегралы, функции нескольких переменных и градиентный спуск.

Зачем. Помогает находить наилучшие (оптимальные) решения и обучать алгоритмы. Производная показывает скорость и направление изменений. Алгоритм градиентного спуска использует производные, чтобы заставлять нейросети и модели машинного обучения совершать всё меньше ошибок. Это главный механизм «обучения» ИИ.


4. Теорвер и матстат: дискретные и непрерывные случайные величины, распределения, теорема Байеса, корреляция, центральная предельная теорему, А/B-тестирование, гипотезы, p-value.

Зачем. Учит принимать обоснованные решения в условиях неопределенности. Статистика нужна, чтобы измерять взаимосвязи через A/B-тесты (например, действительно ли новая кнопка на сайте увеличила продажи или это просто случайность) и оценить надежность выводов.


Можно прийти даже с забытыми школьными знаниями. Формулы разбирают на понятных жизненных задачах с кодом на Python и визуализациями. Есть преподаватель математики, который отвечает на вопросы по сложным задачам, а встроенный ИИ-помощник объяснит одну и ту же формулу разными словами.

💻 Протестировать платформу и формат обучения, а также пройти первый урок бесплатно: https://tprg.ru/WcrJ
Please open Telegram to view this post
VIEW IN TELEGRAM
1
Please open Telegram to view this post
VIEW IN TELEGRAM
2
Python: задачки и вопросы
Развёрнутое пояснение:

1. Вызов await t(1) запускает первую корутину: на печать идёт 1, затем await sleep(0) приостанавливает выполнение main и отдаёт управление event loop.

2. create_task(t(3)) только планирует фоновую задачу в очередь event loop, но не запускает её немедленно.

3. await t(2) печатает 2 и тоже приостанавливается на sleep(0).

4. Event loop видит три готовых продолжения: t(1), запланированная t(3) и main после t(2). Порядок FIFO, поэтому сначала возобновляется t(1), которая печатает 2 и завершается.

5. Следующей запускается t(3): печатается 3, затем await sleep(0) приостанавливает её.

6. Затем event loop возвращает управление в main после await t(2), где сразу выполняется await x и main ждёт завершения t(3).

7. Event loop возобновляет t(3), печатается 4, задача завершается.

8. В результате на печать идёт последовательность 122334.

Почему это важно: в асинхронном коде побочные эффекты и порядок записи строк не всегда совпадают с порядком выполнения. sleep(0) — не пустая операция, а точка уступки управления, после которой event loop выбирает следующую задачу из очереди. Это влияет на порядок логов, обновление кэша, коммитов состояния и других операций с побочными эффектами, поэтому важно понимать, что create_task планирует задачу, а await передаёт управление.
2
Please open Telegram to view this post
VIEW IN TELEGRAM
1
Python: задачки и вопросы
Развёрнутое пояснение:

1. В строке from decimal import Decimal импортируется тип Decimal.

2. Выражение Decimal('0.1') + Decimal('0.2') выполняет точное десятичное сложение и даёт Decimal('0.3').

3. Сравнение a == 0.3 сравнивает Decimal с float. Python преобразует float 0.3 в Decimal через его двоичное приближение, которое не равно Decimal('0.3'), поэтому результат False.

4. Сравнение a == Decimal('0.3') сравнивает два одинаковых Decimal, поэтому True.

5. float(a) превращает Decimal('0.3') в float 0.3, и сравнение с литералом 0.3 даёт True.

6. Итоговый вывод: False True True.

Почему это важно: В финансовых расчётах и работе с ценами часто используют Decimal, чтобы избежать ошибок float. Но при смешивании Decimal и float в сравнениях, сортировках или условиях результат может оказаться неожиданным: равенство может быть ложным, а max или min может выбрать не тот элемент. Правильно — приводить оба операнда к Decimal или к float явно и не полагаться на неявное преобразование.
2