1. This site uses cookies. By continuing to use this site, you are agreeing to our use of cookies. Learn More.
  2. Anuncie Aqui
    Anuncie aqui você Também: fdantas@4each.com.br

[Python] How to compose functions through purely using Python's standard library?

Discussão em 'Python' iniciado por Stack, Junho 26, 2025.

  1. Stack

    Stack Membro Participativo

    Python's standard library is vast, and my intuition tells that there must be a way in it to accomplish this, but I just can't figure it out. This is purely for curiosity and learning purposes:

    I have two simple functions:

    def increment(x):
    return x + 1

    def double(x):
    return x * 2


    and I want to compose them into a new function double_and_increment. I could of course simply do that as such:

    double_and_increment = lambda x: increment(double(x))


    but I could also do it in a more convoluted but perhaps more "ergonomically scalable" way:

    import functools

    double_and_increment = functools.partial(functools.reduce, lambda acc, f: f(acc), [double, increment])


    Both of the above work fine:

    >>> double_and_increment(1)
    3


    Now, the question is, is there tooling in the standard library that would allow achieving the composition without any user-defined lambdas, regular functions, or classes.

    The first intuition is to replace the lambda acc, f: f(acc) definition in the functools.reduce call with operator.call, but that unfortunately takes the arguments in the reverse order:

    >>> (lambda acc, f: f(acc))(1, str) # What we want to replace.
    >>> '1'
    >>> import operator
    >>> operator.call(str, 1) # Incorrect argument order.
    >>> '1'


    I have a hunch that using functools.reduce is still the way to accomplish the composition, but for the life of me I can't figure out a way to get rid of the user-defined lambda.

    Few out-of-the-box methods that got me close:

    import functools, operator

    # Curried form, can't figure out how to uncurry.
    functools.partial(operator.methodcaller, '__call__')(1)(str)

    # The arguments needs to be in the middle of the expression, which does not work.
    operator.call(*reversed(operator.attrgetter('args')(functools.partial(functools.partial, operator.call)(1, str))))


    Have looked through all the existing questions, but they are completely different and rely on using user-defined functions and/or lambdas.

    Continue reading...

Compartilhe esta Página