Python - функция декоратора, использующая лямбда-функцию для класса - PullRequest
0 голосов
/ 29 февраля 2020

Я проверял некоторый код в Интернете о том, как отслеживать шаг указанного c конвейера, и я получил следующий код:

class Pipeline():
    def __init__(self, step_id, fct_to_call):
        self.step_id = step_id
        self.fct_to_call = fct_to_call

    def __call__(self, *args):
        return self.fct_to_call(*args)

def pipeline_step(step_id):
    return lambda f: Pipeline(step_id=step_id, fct_to_call=f)

@pipeline_step(step_id='lacocouracha')
def my_sum(numba):
    output = numba *1.45
    return output

a = my_sum(12)

Мой вопрос связан с тем, когда мы используем лямбда-функцию , Когда я запускаю в режиме отладчика, я вижу, что лямбда-функция «f» ссылается на «my_sum». Таким образом, при использовании лямбда-функции внутри функции декорации, она автоматически поймет, что это декорированная функция, которую она хочет вводить?

Большое спасибо!

1 Ответ

1 голос
/ 29 февраля 2020

Строго говоря, pipeline_step не декоратор; он возвращает декоратор, который является функцией, которая принимает декорированную функцию в качестве аргумента.

pipeline_step можно было бы также написать с помощью оператора def, что может сделать его более явно:

def pipeline_step(step_id):
    def decorator(f):
        return Pipeline(step_id=step_id, fct_to_call=f)
    return decorator

Когда вы вызываете pipeline_step(step_id='lacocouracha'), он возвращает новую функцию decorator (которая действует как замыкание вокруг переменной step_id). decorator затем получает функцию my_sum в качестве аргумента, а имя my_sum возвращается к экземпляру Pipeline, возвращаемому decorator.

Использование лямбда-выражения просто пропускает шаг необходимость придумать имя для декоратора, которое никогда не будет видно или использоваться вне самого pipeline_step.


Для полноты напоминание, что

@pipeline_step(step_id='lacocouracha')
def my_sum(numba):
    output = numba *1.45
    return output

syntacti c сахар для

def my_sum(numba):
    output = numba *1.45
    return output

my_sum = pipeline_step(step_id='lacocoracha')(my_sum)
# == (lambda f: Pipeline(step_id=step_id, fct_to_call=f))(my_sum)
# == Pipeline(step_id=step_id, fct_to_call=my_sum)
...