def test(a, b=[]):
b.append(a)
return b
print(test(1))
print(test(2, [3]))
Результат выполнения кода:
[1]
[3, 2]
Объяснение:
Функция test
имеет аргумент по умолчанию b=[]
. Это означает, что b
инициализируется пустым списком только один раз при определении функции. При первом вызове test(1)
, к этому общему списку добавляется 1
, и возвращается [1]
.
При втором вызове test(2, [3])
, аргумент b
явно передается как [3]
. К этому новому списку добавляется 2
, и возвращается [3, 2]
.
Эта задача иллюстрирует классическую ловушку, связанную с использованием изменяемых объектов (в данном случае, списка) в качестве значений аргументов по умолчанию в Python.
Если бы мы сделали еще один вызов `print(test(4))`, то результат был бы `[1, 4]`, а не `[4]`, как можно было бы ожидать. Это происходит потому, что `b` в первом вызове `test(1)` и последующих вызовах без явного указания `b` - это один и тот же объект списка в памяти.
Чтобы избежать этой проблемы, рекомендуется использовать `None` в качестве значения по умолчанию для аргумента, а затем проверять, является ли аргумент `None` внутри функции. Если да, то создавать новый список:
def test_safe(a, b=None):
if b is None:
b = []
b.append(a)
return b
print(test_safe(1))
print(test_safe(2, [3]))
print(test_safe(4))
В этом случае, каждый вызов `test_safe` без явного указания `b` будет начинать с нового пустого списка.