En Python, me gustaría escribir una función make_cylinder_volume(r)
que devuelva otra función. Esa función devuelta debe ser invocable con un parámetro h
y devolver el volumen de un cilindro con altura h
y radio r
.
Sé cómo devolver valores de funciones en Python, pero ¿cómo devuelvo otra función ?
python
function
functional-programming
currying
Julian Das
fuente
fuente
Respuestas:
Pruebe esto, usando Python:
import math def make_cylinder_volume_func(r): def volume(h): return math.pi * r * r * h return volume
Úselo así, por ejemplo con
radius=10
yheight=5
:volume_radius_10 = make_cylinder_volume_func(10) volume_radius_10(5) => 1570.7963267948967
Tenga en cuenta que devolver una función fue una simple cuestión de definir una nueva función dentro de la función y devolverla al final, teniendo cuidado de pasar los parámetros apropiados para cada función. Para su información, la técnica de devolver una función de otra función se conoce como curado .
fuente
10
que pasaste está guardado en algún lugar? ¿Cuándo se recoge la basura?Usando lambdas, también conocidas como funciones anónimas, puede abstraer la
volume
función dentro de lamake_cylinder_volume_func
en una sola línea. De ninguna manera diferente a la respuesta de Óscar López, la solución con lambda sigue siendo en cierto sentido 'más funcional'.Así es como puede escribir la respuesta aceptada usando una expresión lambda:
import math def make_cylinder_volume_fun(r): return lambda h: math.pi * r * r * h
Y luego llame como lo haría con cualquier otra función curry:
volume_radius_1 = make_cylinder_volume_fun(1) volume_radius_1(1) => 3.141592653589793
fuente
lambda h:
se eliminara, ¿la función funcionaría igual?return
intentará evaluar el resultado antes de regresar, y debido a que es un montón de variables, devolverá algún valor flotante (intente devolver una función y funcionará).lambda
le dice que el siguiente código no debe evaluarse y también que el alcance de la variable r se conservará en las funciones devueltas pormake_cylinder..
.Solo quiero señalar que puedes hacer esto con pymonad
import pymonad @pymonad.curry def add(a, b): return a + b add5 = add(5) add5(4) 9
fuente
from functools import partial add5 = partial(add, 5)
Hace exactamente lo mismoSé que llego demasiado tarde a la fiesta, pero creo que esta solución puede resultarle interesante.
from math import pi from functools import partial def cylinder_volume(r, h): return pi * r * r * h make_cylinder_with_radius_2 = partial(cylinder_volume, 2) make_cylinder_with_height_3 = partial(cylinder_volume, h=3) print(cylinder_volume(2, 3)) # 37.6991118431 print(make_cylinder_with_radius_2(3)) # 37.6991118431 print(make_cylinder_with_height_3(2)) # 37.6991118431
Aquí hay documentación sobre cómo
partial
funciona.fuente