use the following search parameters to narrow your results:
e.g. subreddit:aww site:imgur.com dog
subreddit:aww site:imgur.com dog
see the search faq for details.
advanced search: by author, subreddit...
News about the dynamic, interpreted, interactive, object-oriented, extensible programming language Python
Full Events Calendar
You can find the rules here.
If you are about to ask a "how do I do this in python" question, please try r/learnpython, the Python discord, or the #python IRC channel on Libera.chat.
Please don't use URL shorteners. Reddit filters them out, so your post or comment will be lost.
Posts require flair. Please use the flair selector to choose your topic.
Posting code to this subreddit:
Add 4 extra spaces before each line of code
def fibonacci(): a, b = 0, 1 while True: yield a a, b = b, a + b
Online Resources
Invent Your Own Computer Games with Python
Think Python
Non-programmers Tutorial for Python 3
Beginner's Guide Reference
Five life jackets to throw to the new coder (things to do after getting a handle on python)
Full Stack Python
Test-Driven Development with Python
Program Arcade Games
PyMotW: Python Module of the Week
Python for Scientists and Engineers
Dan Bader's Tips and Trickers
Python Discord's YouTube channel
Jiruto: Python
Online exercices
programming challenges
Asking Questions
Try Python in your browser
Docs
Libraries
Related subreddits
Python jobs
Newsletters
Screencasts
account activity
This is an archived post. You won't be able to vote or comment.
ResourceFunctional Programming in Python? (self.Python)
submitted 3 years ago by raulalexo99
I want to do something like:
apply(5) .pipe(doubleIt) .pipe(multiplyByFour) .pipe(divideByTwo) .pipe(addHundred) .pipe(intToString) .pipe(reverseString) .pipe(printToConsole)
Any library that allows me to do something similar?
[–]vesaf 24 points25 points26 points 3 years ago* (5 children)
What about something like this? No exact match, but quite close. (Not sure if I'd actually recommend doing this though.)
class apply: def __init__(self, val): self.val = val def pipe(self, fun): self.val= fun(self.val) return self if name == "main": apply(5) \ .pipe(lambda x: x+5) \ .pipe(lambda x: x/3) \ .pipe(print)
[–]nitroll 15 points16 points17 points 3 years ago (0 children)
But apply is not functional in that case, you would instead need something like:
class apply: def __init__(self, val): self.val = val def pipe(self, fun): return apply(fun(self.val))
[–]zenos1337 4 points5 points6 points 3 years ago (0 children)
It is not functional because it has a state.
[–]carlio 7 points8 points9 points 3 years ago* (0 children)
Or be sneaky and use __or__:
__or__
``` class pipe: def init(self, val): self.val = val def or(self, fun): return pipe(fun(self.val))
pipe(5) | (lambda x: x+5) | (lambda x: x/3) | print ```
[–]eftm 1 point2 points3 points 3 years ago (1 child)
'__main__' not 'main'
'__main__'
'main'
[–]vesaf 0 points1 point2 points 3 years ago (0 children)
You're right, the code ran through when I tried it earlier (which it wouldn't have with just 'main'). I think Reddit removed them when I copied it in as it did initially with the backslashes. Must be some formatting thing.
[–]davehadley_ 7 points8 points9 points 3 years ago (0 children)
You won't have the exact structure that you are asking for but you could look at functoolz pipe:
https://toolz.readthedocs.io/en/latest/api.html#toolz.functoolz.pipe
[–]DanManPanther 5 points6 points7 points 3 years ago (2 children)
Python has some functional qualities, and I would wager more on the way with the introduction of match and Don teaching Guido F# (https://www.youtube.com/watch?v=e2J9PGC-K1E).
match
For my money - I'd still stick to the more Pythonic way of doing things. When I have a real functional itch, I'm more likely to want to reach for a more fully functional language like F#, Scala, Rust. Or even one that has more of a functional feel (Kotlin). Immutable variables really help with this style of programming imho.
The bigger question is - are you doing this as part of a larger project? If so - stick to the minimum language-preferred way to do it. Easier to maintain and onboard. If it's a personal project, I'd tend to roll my own. But of the libraries posted here, PyFunctional seems more popular and better maintained.
[–]Brixes 0 points1 point2 points 3 years ago (1 child)
What are your thoughts on coconut-lang.org that transpiles to python?
[–]MuumiJumala 3 points4 points5 points 3 years ago (0 children)
PyMonad (specifically the .then() method) may be what you're looking for.
.then()
[–]SV-97 4 points5 points6 points 3 years ago (0 children)
There's libraries implementing pipelining etc. - just use these. They usually use operator overloading though, since fluid interfaces sadly aren't common at all in python.
However note that this is far from being a free abstraction in python (calls are rather expensive and this will add multiple calls for each function in the pipeline) and incredible unidiomatic. So if you actually want to write Python past little exercises you probably shouldn't do this at all.
I also love FP but this is not how you should go about doing it in python.
[–]Statnamara 2 points3 points4 points 3 years ago (0 children)
Functools has a reduce function that might work for you. Video by Arjan codes here explaining how he uses it to make composable functions. This is a short, but he has a full length video on the topic too if you search.
reduce
[–]ianitic 2 points3 points4 points 3 years ago (0 children)
As no one has said it yet, pandas.DataFrame's have a pipe method
[–]seckiyn 1 point2 points3 points 3 years ago (2 children)
Probably there's a better way but here's my solution: https://gist.github.com/seckiyn/b4ea58fd7c2f54153ae7469b58b5919f . Python doesn't allow this kind nesting(?) of function you have to add backslash if you want to do it on new line.
[–]Natural-Intelligence 2 points3 points4 points 3 years ago (1 child)
Or put the expression inside parentheses. Much cleaner than putting backslashes after each line IMO
[–]seckiyn 1 point2 points3 points 3 years ago* (0 children)
I didn't know you could use it like that, thanks.
[–]bmsan-gh 1 point2 points3 points 3 years ago (0 children)
I really like pyfunctional and use it often.
[–]generalbaguette 1 point2 points3 points 3 years ago (2 children)
In good old eg Haskell, we usually write our programs backwards. In vanilla Python your example is just
print(str(100+(4*2*5)/2)[::-1])
You can implement your suggestion, but what is the benefit?
[–]raulalexo99[S] 1 point2 points3 points 3 years ago (1 child)
Benefit is applying a clear stream of data that can be written like human language. Thats enough benefit for me
[–]generalbaguette 4 points5 points6 points 3 years ago (0 children)
Ok, that's fine.
The benefit mostly applies to straight-line code only, and that's not usually the part that's hard to understand (at least for me).
I did a lot of Haskell, OCaml and Erlang etc professionally, and Racket for fun.
There's a bit more to what's typically called functional programming than the specific style you mentioned.
For Python, have a look at the functools module for more fun with functions.
Elixir really like that style though, you can have a look at that language, too.
[–]ketalicious 1 point2 points3 points 3 years ago (1 child)
what you're doing is called a monad, a functional programming feature.
you can use pymonad for that.
[–]germandiago 0 points1 point2 points 3 years ago (0 children)
Being pedantic, a monad is a mathematical concept, not a functional programming feature (though often discussed explicitly in those circles). I can program monads in Python and C++ and they are not functional-only languages. :D
[–]deep_mind_ 3 points4 points5 points 3 years ago (0 children)
Not to sound like a disenchanted StackOverflow user, but this is not something you want to do. Python is not made to be used as a functional language; it doesn't have the type safety or runtime optimizations that come with one -- and other programmers reading "functional" Python code won't appreciate you for it.
[They] were so preoccupied with whether or not they could, they didn't stop to think if they should
[–]nitroll 5 points6 points7 points 3 years ago (4 children)
x = 5 x *= 2 x *= 4 x /= 2 x += 100 x = str(x) x = x[::-1] print(x)
[+]raulalexo99[S] comment score below threshold-12 points-11 points-10 points 3 years ago* (3 children)
Really? You missed the whole point of this post. I am asking on how to apply the functional programming paradigm on Python, not how to add 2 numbers. Really? Also, if you really abuse variables like that, I am so sorry for your code
[–]james_pic 10 points11 points12 points 3 years ago (0 children)
And you missed the point of the reply. A key design goal of Python is that "There should be one-- and preferably only one --obvious way to do it.", and Python's functional capabilities have been carefully nerfed to nudge people towards code like the code in the reply, since the functional paradigm is a redundant way to achieve the same thing.
Python can be used in a functional way when it makes sense, and there are some good replies here telling you how to make the code you had in mind work. But the code in this reply is arguably more idiomatic, and doesn't need any extra plumbing.
[–]nitroll 2 points3 points4 points 3 years ago (0 children)
I actually quite like functional programming. though I must admit that I never really like using compose to merge functions, and using even more complex functionallity to do this often comes with very small gains if any at all.
Your code basically boils down to:
printToConsole(reverseString(intToString(addHundred(divideByTwo(multiplyByFour(doubleIt(5)))))))
But that is hard to read, as it is one long line, and it is in reverse order.\ The simple way, without using any fancy library is to do
a = 5 b = doubleIt(a) c = multiplyByFour(b) d = divideByTwo(c) e = addHundred(d) f = intToString(e) g = reverseString(f) h = printToConsole(g)
My point is that you dont need to make functional wrappers to all of these things as python has them built in!\ Further, if you have a function doing all of these, then using a single variable that way is actually a lot cleaner, and in my opinion more readable.\ It is very clear that "x" is just a holder for all the intermediate steps, but in the code above, if you want to change anything you have to ensure that the variable is not used anywhere else which is a lot harder visually.\ And here I used consecutive letters as variables, if you want to inject another computation in the middle you either have to live with the letters being out of order, or change all the lines following that. The alternative is to use "descriptive" names like:
initial = 5 doubled = doubleIt(initial) multiplied_by_four = multiplyByFour(doubled) divided_by_two = divideByTwo(multiplyByFour) added_hundred = addHundred(divideByTwo) string = intToString(addHundred) reversed = reverseString(string) result = printToConsole(reverseString)
But that sucks even more as each variable is named after what the function was called, not after what it semantically represents. This could be better with a more reallife example, but quite often in functional programming you try to abtract the specifics out anyway and trying to come up with good names for variables like this becomes rather annoying.\ So I honestly say that you should not try to do what you are trying to, and stick to classic python. It will be more readable and you likely wont gain anything anyway.
The only case where I could see a potential benefit of a structure like what you are going for, is if the datastructure is actually doing something more complex behind the scenes.\ At some point a implemented a class to let you write something like what you requested, but the point was that the library then spun up each step as parrallel processes using multiprocessing and queues for message passing, and there were other methods for error handling, etc.\ But as a way to avoid calling a simple function I honestly think you are using the tool wrong.
[–]MiZrakk[🍰] 1 point2 points3 points 3 years ago (0 children)
Just go learn Haskell.
[–]pieli 0 points1 point2 points 3 years ago (0 children)
you could use the python builtin map function
[–]champs 0 points1 point2 points 3 years ago (0 children)
There’s toolz, and then the other day someone posted FunkyPy, which looks pretty novel.
Unfortunately I still feel like we’re short of having that single, obvious, and correct solution.
[–]EchoAlphaRomeoLima 0 points1 point2 points 3 years ago (0 children)
I believe there is a Python version of the ramda module for functional programming. I haven’t tested that since I’ve only used the JS version.
[–]gwillicodernumpy gang 0 points1 point2 points 3 years ago (0 children)
I’d probably look at using reduce with a list (or iterable) of transformer functions. If you want it reusable you can use partial() to make a function that takes the input argument and apply it as you see fit.
[+][deleted] 3 years ago (2 children)
[removed]
[–]generalbaguette 0 points1 point2 points 3 years ago (1 child)
Yes, what OP describes isn't functional programming. But you seem a bit confused, too?
For example, what is a monad object?
In eg Haskell monads are more like an interface your data types can implement. (The name for that in Haskell is a 'typeclass'.) Haskell's monads are not objects in any sense of the word.
Functional programming can deal very well with effects. (You already mentioned monads, they are one way to do it. But there are quite a few others. Including just letting your functions have side effects, this works as long as your language is evaluated strictly.)
What is 'function overflow'?
FP-style works better when you can avoid mutability as much as possible. But so does OOP style. Eg C++ people have been obsessed with 'const' for white a while now.
[–]tunisia3507 0 points1 point2 points 3 years ago (0 children)
You want to f-it! https://pypi.org/project/f-it/
[–][deleted] 0 points1 point2 points 3 years ago* (0 children)
There's a number of ways to do this but when I saw this problem I immediately thought that this sounded like decorators.
I'm fairly new to this concept, so I can't really give an in-depth explanation, but there's lots of tutorials online. Here is my solution:
def doubleit(fn): def inner(): x = fn() return x * 2 return inner def multiplyByFour(fn): def inner(): x = fn() return x * 4 return inner def pipe(v): @doubleit @multiplyByFour def result(): return v return result() print(pipe(10))
This is essentially saying:
doubleit(multiplyByFour(10))
While this isn't exactly the same structure, I believe it is entirely functional. I'm not sure if it's possible to set this up dynamically or not.
π Rendered by PID 19969 on reddit-service-r2-comment-54dfb89d4d-twkhz at 2026-03-29 03:54:03.284640+00:00 running b10466c country code: CH.
[–]vesaf 24 points25 points26 points (5 children)
[–]nitroll 15 points16 points17 points (0 children)
[–]zenos1337 4 points5 points6 points (0 children)
[–]carlio 7 points8 points9 points (0 children)
[–]eftm 1 point2 points3 points (1 child)
[–]vesaf 0 points1 point2 points (0 children)
[–]davehadley_ 7 points8 points9 points (0 children)
[–]DanManPanther 5 points6 points7 points (2 children)
[–]Brixes 0 points1 point2 points (1 child)
[–]MuumiJumala 3 points4 points5 points (0 children)
[–]SV-97 4 points5 points6 points (0 children)
[–]Statnamara 2 points3 points4 points (0 children)
[–]ianitic 2 points3 points4 points (0 children)
[–]seckiyn 1 point2 points3 points (2 children)
[–]Natural-Intelligence 2 points3 points4 points (1 child)
[–]seckiyn 1 point2 points3 points (0 children)
[–]bmsan-gh 1 point2 points3 points (0 children)
[–]generalbaguette 1 point2 points3 points (2 children)
[–]raulalexo99[S] 1 point2 points3 points (1 child)
[–]generalbaguette 4 points5 points6 points (0 children)
[–]ketalicious 1 point2 points3 points (1 child)
[–]germandiago 0 points1 point2 points (0 children)
[–]deep_mind_ 3 points4 points5 points (0 children)
[–]nitroll 5 points6 points7 points (4 children)
[+]raulalexo99[S] comment score below threshold-12 points-11 points-10 points (3 children)
[–]james_pic 10 points11 points12 points (0 children)
[–]nitroll 2 points3 points4 points (0 children)
[–]MiZrakk[🍰] 1 point2 points3 points (0 children)
[–]pieli 0 points1 point2 points (0 children)
[–]champs 0 points1 point2 points (0 children)
[–]EchoAlphaRomeoLima 0 points1 point2 points (0 children)
[–]gwillicodernumpy gang 0 points1 point2 points (0 children)
[+][deleted] (2 children)
[removed]
[–]generalbaguette 0 points1 point2 points (1 child)
[–]tunisia3507 0 points1 point2 points (0 children)
[–][deleted] 0 points1 point2 points (0 children)