Mutable default-аргументы в Python (на примере списка)
@python_quizРазберем этот квиз
Код из квиза:

Кратко о ключевой идее
- Значение default-параметра создаётся один раз при определении функции, а не при каждом вызове.
- Если этот default-объект изменяемый (например, список), то все вызовы функции без явного аргумента будут работать с одним и тем же объектом и видеть его изменения.
Демонстрация поведения

Что получилось
- Переменные a и b ссылаются на один и тот же список (default-список), поэтому после второго вызова оба становятся [1, 2].
- Переменная c получает новый список, переданный явно [], и становится [3].
Анализ вариантов ответов
- "a=[1], b=[1], c=[3]" — не соответствует поведению: b изменит default-список, поэтому b (и a) не останутся [1].
- "a=[1], b=[1,2], c=[3]" — не соответствует: хотя b действительно [1,2], a после изменения тоже указывает на тот же список и станет [1,2].
- "a=[1], b=[2], c=[3]" — не соответствует: невозможно, потому что вызов f(2) добавляет 2 к тому же списку, где уже есть 1.
- "a=[1], b=[1,2,3], c=[3]" — не соответствует: b не станет [1,2,3] в этом примере (не было третьего без-аргументного вызова), и a тоже изменится вместе с b.
Правильный итог: a и b — один и тот же изменяемый default-список [1, 2], c — отдельный список [3].
Как избежать неожиданных эффектов
Если вы хотите, чтобы при каждом вызове создавался новый список по умолчанию, используйте None и создавайте список внутри функции:

Вывод
- Изменяемые default-аргументы в Python сохраняют состояние между вызовами функции, что часто приводит к неожиданному поведению.
- Предпочтительный паттерн — использовать None как маркер и создавать новый объект внутри функции, если нужен fresh default.