Repeat a function composition n times in Python like Haskell's repeat

若如初见. 提交于 2020-12-26 18:49:43

问题


This code does NOT work:

def inc(x):
    return x + 1

def repeat(f, n):
    if n == 0:
        return lambda x: x
    else:
        return f( repeat(f, n - 1 ) )

inc_10 = repeat(inc, 10)

#TypeError: unsupported operand type(s) for +: 'function' and 'int'


'''
# Ideally
print(inc_10(0))
# 10
'''

How can I write it in a more Pythonic way or in lambda calculus way ?


回答1:


You still need to return a function, not the result of calling f, in the recursive case.

# repeat :: (a -> a) -> Integer -> a -> a
# repeat _ 0 = id
# repeat f n = \x -> f (repeat f (n-1) x)
def repeat(f, n):
    if n == 0:
        return lambda x: x
    else:
        return lambda x: f (repeat(f, n-1)(x))

It's a little easier to read if you define a composition function as well:

def identity(x):
    return x


def compose(f, g):
    return lambda x: f(g(x))


# repeat :: (a -> a) -> Integer -> (a -> a)
# repeat _ 0 = id
# repeat f n = f . repeat f (n - 1)
def repeat(f, n):
    if n == 0:
        return identity
    else:
        return compose(f, repeat(f, (n-1)))

Or using functools.reduce:

# repeat :: (a -> a) -> Integer -> (a -> a)
# repeat f n = foldr (.) id $ replicate n f
def repeat(f, n):
    return reduce(compose, [f]*n, identity)


来源:https://stackoverflow.com/questions/60455964/repeat-a-function-composition-n-times-in-python-like-haskells-repeat

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!