Functional Programming Sucks*

(*like everything else that is mindlessly applied the wrong way to solve the wrong problems)

Functional Programming Rocks!
You can do amazing things with Haskell. The historical importance of Lisp is huge. Math, computer science, algorithms and engineering can come together beautifully with functional programming. Writing small reusable, testable functions with no side effects is a great thing to do in any language – but more than anywhere else those virtues are emphasized in functional programming. I love first class functions!


The unfortunate JavaScript Hype
As JavaScript made map, filter and reduce part of the standard those have become the foremost frontier of functional programming. Being quite serious, many people argue that if you replace your for-loops with map, filter, reduce and forEach you have achieved something significant when it comes to readability. What do you think?

// non-functional smelly loop
redFruits = [];
for ( f in fruits ) {
  if ( 'red' === fruits[f].color ) redFruits.push(fruits[f]);

// fantastic functional alternative
greenFruits = fruits.filter(function(f) {
  return 'green' === f.color;

As a bonus with functional, you can use lamda-functions… that is functions, with no name, that can not be reused. You can even use arrow-functions if you think this is too easy a concept and you think the code gets more readable by omitting the confusing word function.

While there are a lot of balanced articles about using functional ideas in JavaScript, for a lot of people eliminating for-loops at any cost seems to be functional enough.

The argument here is that your code should be declarative, it should express intention rather than instructions. In the case above with the fruit-filter it does make some sense. But if that argument should make any sense, it requires that the programmer does not abuse map, filter, forEach or reduce to eliminate a for-loop just for the sake of it. I have seen things like:

// functional
applePrice = fruits[Object.keys(fruits).filter(function(f) {
  return 'apple' === fruits[f].name;

// when this would work
for ( f in fruits ) {
  if ( 'apple' === fruits[f].name ) {
    applePrice = fruits[f].price;

I have several objections with the functional version. The Object.keys thing is hardly pleasant to the eye. It is false marketing to use filter: the intention is find or search, not filter. So you still need to read the details (just as with the for-loop), you are just first fooled into thinking its a filter (and chaining is very popular, so then you have no function names and no variable names). But perhaps the worst problem is the lack of error handling. Functional code is not meant to have side effects, and error handling is exactly that. If ‘apple’ is not found you get an ugly Error. You can of course try/catch, or make temporary array variable apples and check that its length is one, but people who prefer functional style usually dont do it.

I understand your objection: people can write crappy code with any language an paradigm and just becuase I have seen bad applications of filter does not mean there is anything wrong with filter or FP. Of course. The bad thing is recommending people to use it like a silver bullet. The bad thing is that good FP is actually difficult and junior programmers will get it wrong trying to be fashionable.

Here is another example to show I am not inventing this rant.

Functional is preferable-Hype
Another favorite example of this functional hype is from rosettacode. Look at this amazing collection of implementations of a simple algorithm: the Luhn Algorithm. I suggest:

  1. Read the introduction so you get some idea
  2. Look at the C-implementation: imperative and simple. Testable and no side effects.
  3. Look at the functional implementations: C++11, Common Lisp, Haskell, JavaScript (ES5.1 version), PicoLisp, Python, Rust, Scheme

Update: this is what the Luhn Algoritm looked like when this article was written: (link to Rosetta Code).

Look at Scala: there are two versions, a Functional Style and an Imperative style. The people att IOCCC would be jealous with this shit!

I can only come to one conclusion: the emperor is naked.

I mean, if you code in PicoLisp, for fun or for a good reason, and you have to implement the Luhn algorith, please do so! But to say “recommended” about the functional Scala code or to think that the C++11 code is in anyway more reasonable than the original C-code… it makes no sense. No real systems programmers will choose Rust over C based on this. And Python – a language known for its clarity… such a sad example.

Trendy fashionable “functional programmers” suck
So, the problem here is not primarily with Function Programming itself or the code that guru coders write with Functional Programming. The problem is that people with far too little theoretical background, training and experience follow the hype and the result is ugly.

Functional Programming Sucks (at)
There are some things that Functional Programming is not very good at: State and Side Effects. This is by design. From a FP perspective (and a general perspective as well) State and Side Effects are nasty and problematic: they should be avoided and when they cant be avoided they need special attention (like Monads).

The problem here is that JavaScript is mostly a programming language for the web. A simple (modern, single page) web application:

  1. Loads data from a server
  2. Presents data to the user
  3. Lets the user update the data
  4. Sends the data back to the server

This is (almost) all about state and side effects! You may have some functions for validation, filtering, sorting and calculations on the client, and those benefit from Functional Programming ideas. But your core enterprise is about state, side effects and error handling! Functional Programming is so unsuitable for this that a simple web page just can’t be written functionally, unless you start breaking rules. And this is of course what programmers end up doing because in the end of the day they have a real application to build for real users.

The difficult thing is to break the right rules in the right way at the right place for the right reason. This is architecture – mixing concepts, and designing how your application lives, its breaths and heartbeats. Architecture is difficult, and it is not made easier relying on unsuitable silver bullets.

Edit: however check the link in the bottom of this article.

Functional Reactive Programming
There is one thing that is even more hyped and even more theoretic than Functional Programming, and that is Functional Reactive Programming.

But it makes sense (as I understand it). It is not about taking Functional Programming one step further but about putting it in context. You have data that changes (signals, events, behaviours, whatever). That data can be pipelined with high quality through FP logic to produce the content of your GUI or the requests to the server.

Keep the functional parts functional, and let other parts of your application just deal with I/O, GUI and state. Dividing your code into separate modules with clear responsibilites and clear interactions have always been a good idea.

My experience is that when a real world application is not well received by the users a lot of the time its because performance sucks. When performance is bad usability is also bad, and stability gets bad (especially on the server side).

Functional programming is typically bad for performance.

  • anonymous functions can often not be JIT compiled and will never be optimized
  • recursion is nice, but rarely faster than a loop
  • the chaining concept creates arrays and arrays and arrays just for throwing away, which is fun for the garbage collector, but it is not fast
  • the immutable object concept is about generating new RO copies of object instead of changing objects, which is expensive and wasteful

Perhaps worse, since functional programming and proper use of and map(), filter(), reduce() and friends is hard (easy things get difficult) not so experienced programmers end up writing implementations with unnecessary computational complexity ( O(n) turns into O(n^2) ). It is not funny – you cant afford that for most anything that goes to production.

Agile, refactoring and generic code
It is HARD to design code properly from the beginning! Good objects, classes, functions, modules, packages, namings, dependency trees and architecture dont come for free! Agile and Refactoring are about accepting that the design will not be optimal the first time, thus we should not bother too much about it, but rather fix the code when we have learnt more about the problem and our code starts getting (too) ugly.

A strong argument for FP is that it is highly generic – which is true. But until a programmer has spent much time with her domain and problem she will not know what things can and should be made generic. Making things too generic is called overengineering, and it is perhaps the worst sickness in our industry.

I usually:

  • start with one source file rather than many
  • allow myself some copy-paste until I see what code really gets repeated
  • make my code as specific as possible, unless I see an obvious generalisation or the actual need for generalisation emerges
  • dont worry too much about global variables in the beginning (after a while there will be a natural place for them or for what they represent)
  • allow quite long functions until I see what parts of them actually do something meaningful on its own
  • code quite defensively with lots of error handling (it usually pays of quite quickly)

This works for getting quick practical results. Later, during refactoring, when the code base has grown, and when I have learnt more about the domain, I can break out pieces of critical code that creates nice generic functions. But thinking FP first – no way!

All FP-sucks related articles

Functional Programming is Slow – Revisited
Functional Programming Sucks (this one)
Underscore.js sucks! Lodash sucks!
Functional Programming Sucks! (it is slow)
Lodash Performance Sucks!

Update 2018-01-14: I also wrote Programming paradigms rock and suck! for putting FP and other paradigms in context.
Update 2018-12-15: I wrote Lambda Functions considered Harmful.

  1. I’d like to clarify some things because there’s a lot of misinformation out on what FP is. Although I highly agree with you that it depends on the coder. But that can be said about any paradigm.

    First, don’t hate me bro, but I found some errors in your code. The functional applePrice function does not work. Object.keys creates an array of the object keys, but the filter function returns the actual element that satisfied the predicate.

    The for…in loop you wrote just had a minor mistake. You wrote === “apple”, when it should be fruits[f].name.

    FP can easily deal with side effects and mutations. It’s just a different approach. Not sure if you’ve seen this gitbook, but it was by far what got me to understand FP from a practical perspective.

    Now I’m no FP guru or theoretician (been studying this for 1 month), but I came up with a much better example of functional composition. I had to use lodash since the native methods don’t iterate over objects. You could of course rewrite your for in loop to accept arguments. A common misconception is that you must use the native methods to be functional. Not true. You can write your own imperative, generic functions, so long as the structure of the app is functional.

    So check this out. If you’re writing an app that needs to find the prices of fruits, most likely you’ll need to find the prices of other foods, correct? (btw still using the ‘pre’ tags to format, but sometimes they don’t work)

    const { find } = require('lodash');
    ** curry magic
    const prices = obj => item => find(obj, ['name', item]).price;
    Now because it's curried we can do like so:
    const fruitPrices = prices(fruits);
    const meatPrices = prices(meats);
    Some distance place in your app, you call them like so:

    You can’t tell me that’s not cleaner to the eye. And if the fruitPrice lookup works, but the meats doesn’t, you don’t have to debug the find method because it’s now decoupled.

    Here’s a mock object in case anyone wants to test this for themselves:

    const fruits = {
        a: {
            name: 'apple',
            price: 0.5,
        b: {
            name: 'banana',
            price: 1.25,
        o: {
            name: 'orange',
            price: 0.75,
    const meats = {
        a: {
            name: 'beef',
            price: 5.0,
        b: {
            name: 'chicken',
            price: 3.5,
        c: {
            name: 'tuna',
            price: 0.75,
    console.log(`an apple costs $${fruitPrices('apple')}`);
    console.log(`chicken costs: $${meatPrices('chicken')}`);
  2. Thank you John,

    I indented the code in your post.
    I also fixed (I think) the bugs in my example code.

    The filter one: Obviously I never use filter(), I just read usages of it that appear abusive… so I failed to get it right.
    The for-loop one: I always get confused because in Angular when you make a loop you get the object, not the key. My mistake.

    I appreciate both your examples and the gitbook (that I just started reading).

    It is getting even more clear to me now that it is the abuse/misuse of FP that I dislike, not FP done right.
    And there are some things about FP that I really like that I have not even thought of as FP.

  3. @John Bad boy, bad bad!

    You are adding a dependency (const { find } = require(‘lodash’);) for a really simple example.

  4. John, and what’s the advantage of chaining functions that way (ehm, “functional” programming). You still are defining a function at each time with funny const syntax. I have experience with both and I have NEVER ever seen, even oncel, a case where “FP” improved readability or stability or performance of any software. Not even ONCE and very quite opposite. FP is a generational duck thrown to stand out of the crowd for youngsters, sort of religion. It has little to do with engineeering.

  5. PizzaDances

    `You can do amazing things with Haskell`.
    This is the problem. We, programmers, should not do “amazing things”, we should make programs! The rule is the one: “LESS WORK, LESS TIME, MORE RESULTS”. The formula of the business. But in the case of Haskell we: 1) have not libraries! 2) existing libraries are buggy and academic 3) no common interfaces, so any library (even standard ones) introduces own eDSLs and approaches 4) a lot of weird and impractical abstractions, so cognitive loading is incredible big 5) very buggy Haskell compiler and stack tool 6) super large installation of just a compiler (40Mb of Python, 40Mb of D, 1Gb of Haskell!!!) 7) theory and abstractions are so detached from the reality that a programmer spends a lot of time without any real results: everything what we can do in Python for 1-2 days will need about 0.5-1 month in Haskell 8) a lot of abandoned libraries 9) bad documentation, lack of good examples, you will find academic articles, papers instead of traditional programmer’s documentation 10) a lot of alternative dependencies, so your app will depend of many similar libraries due to their transitional dependencies 11) Haskell app are very big – Hello world is about 5Mb, usual app is about 40-50Mb 12) Haskell app eats a lot of memory 13) Haskell code sometimes is very slow (it happens) 14) Haskell app has unpredictable behavior: you cannot estimate memory/CPU consumption based on the code analyze like you do it in other languages, Haskell is very far from real CPU architecture and it is based on very weird and impractical approaches, for example, chunks. 15) Laziness of Haskell often leads to very strange errors and memory “leaks” 16) Haskell tooling and ideology in general is from 90s, very old and outdated vision 17) Haskell is not about programming, it’s totally oriented on academia and FP language research, experiments and so on

Leave a Comment

NOTE - You can use these HTML tags and attributes:
<a href="" title=""> <abbr title=""> <acronym title=""> <b> <blockquote cite=""> <cite> <code> <del datetime=""> <em> <i> <q cite=""> <s> <strike> <strong>

Time limit is exhausted. Please reload CAPTCHA.

This site uses Akismet to reduce spam. Learn how your comment data is processed.

Trackbacks and Pingbacks: