Как создать несколько функций в цикле?

Задача такая, я хочу создать несколько функций, причём нужно делать это в цикле.

li = ['f', 'g', 'a']
res = []

for el in li:
    def a():
        return el


    res.append(a)


for func in res:
    print(func())

Вывод при этом будет три 'a', а нужно чтобы было 'f', 'g', 'a'. Возможно ли это вообще сделать на питоне?


Ответы (2 шт):

Автор решения: CrazyElf

У вас проблема с замыканием переменных. Ваша функция возвращает ссылку на переменную цикла, а не на значение этой переменной. Решить эту проблему можно, например, зафиксировав аргумент анонимной функции, захватив таким образом значение переменной:

for el in li:
    res.append(lambda el=el: el)

Другой вариант захватить значение переменной - через дефолтный параметр функции (по сути это тоже самое, что выше сделано через lambda):

for el in li:
    def a(el=el):
        return el
    res.append(a)

Вывод в обоих случаях будет одинаковый:

f
g
a
→ Ссылка
Автор решения: insolor

Внутри функции el - это глобальная переменная, при вызове функции возвращается актуальное значение этой переменной (то что в ней осталось после завершения цикла).

Тут можно использовать функцию, создающую новую функцию, передавать значение через параметр, тогда внутренняя функция будет видеть этот локальный параметр, а не глобальную переменную:

li = ['f', 'g', 'a']
res = []


def create_function(param):
    def a():
        return param
    return a


for el in li:
    res.append(create_function(el))


for func in res:
    print(func())
→ Ссылка