В коде Python: def add_item(item, lst=[]): lst.append(item); return lst — объясните, в чем состоит ошибка при многократных вызовах, почему это важно для обучения программированию и как правильно переписать функцию
Проблема: аргумент по умолчанию `lst=[]` создаётся один раз при определении функции, поэтому один и тот же список используется при всех последующих вызовах. В результате значения накапливаются между вызовами. Пример (поведение функции): ``` print(add_item(1)) # -> [1][1][1]
print(add_item(2)) # -> [1,2][1, 2][1,2] # неожиданно: второй вызов не вернул новый список [2] ``` Почему это важно для обучения: - такие «скрытые» изменяемые состояния приводят к трудноуловимым багам; - понимание scope и времени создания объектов (definition-time vs call-time) критично для надёжного кода; - помогает учиться правильно выбирать неизменяемые sentinels и явную инициализацию. Правильный вариант (стандартный паттерн — использовать `None` как sentinel): ``` def add_item(item, lst=None): if lst is None: lst = [] lst.append(item) return lst ``` Комментарий: если вы намеренно хотите сохранять состояние между вызовами, можно явно завести внешний список или использовать замыкание/атрибут функции, но делать это нужно осознанно.
Пример (поведение функции):
```
print(add_item(1)) # -> [1][1][1] print(add_item(2)) # -> [1,2][1, 2][1,2] # неожиданно: второй вызов не вернул новый список [2]
```
Почему это важно для обучения:
- такие «скрытые» изменяемые состояния приводят к трудноуловимым багам;
- понимание scope и времени создания объектов (definition-time vs call-time) критично для надёжного кода;
- помогает учиться правильно выбирать неизменяемые sentinels и явную инициализацию.
Правильный вариант (стандартный паттерн — использовать `None` как sentinel):
```
def add_item(item, lst=None):
if lst is None:
lst = []
lst.append(item)
return lst
```
Комментарий: если вы намеренно хотите сохранять состояние между вызовами, можно явно завести внешний список или использовать замыкание/атрибут функции, но делать это нужно осознанно.