Decorators

En Python, un decorador es una construcción especial que nos permite añadir funcionalidad extra a una función o clase existente sin modificar su código fuente.

Un decorador es un callable que toma otra función o clase como entrada y devuelve una versión modificada de la misma.

Empecemos con algo que ya hemos visto relacionado con funciones de primera clase, first class functions, i.e., tratar funciones como cualquier otro objeto.

Closures nos daban la ventaja de crear "instancias" de funciones, i.e., llevarnos las variables libres en el entorno de la función en la que fueron creadas una vez que estas funciones se agotaron porque ya fueron ejecutadas.

Podemos simplificar la función, ya que teniendo en cuenta el scope, no necesitamos definir mensaje

Es decir, la variable mensaje no aporta inicialmente nada a la función _innerf

Utilicemos esto para introducir decorators

Un decorator es una función:

1.- Que toma a otra función como argumento

2.- Le añade funcionalidad

3.- Retorna otra funcíón

Todo esto sin alterar el código de la función original dada en 1.

Para verlo, reescribamos la definición de la función anterior en términos de un decorador.

````python def outer_f(msg): def inner_f(): print(msg) return inner_f

Recordemos lo que hace esta función

1.- Retorna un a función que espera que sea ejectuada: wrapper_function

2.- Esa función, cuando se ejectua, imprime el mensaje.

Ahora: por qué no cambiar el print de un mensaje por la ejecución de una función que pasamos como argumento.

Esto es lo que hace un decorador: envuelvo una función orginal con otra función

Claro, no hemos hecho mas nada de lo que hemos visto en closures...agregemos algo de decoración

Un decorador nos permite rapidamente añadir funcinalidad a una función.

Sintaxis:

Que sucede si nuestra función original tiene inputs

Veamos un ejemplo con un gráfico

Añadir flexibilidad: decorador con argumentos

Por ejemplo, si los labels los ejes cambian, o cambia el titulo.

Para ello, tenemos que añadir un nivel