Skip to main content
6 of 6
replaced http://stackoverflow.com/ with https://stackoverflow.com/

Javascript is prototypal first, with functional capabilities - granted by it's use of functions as first class objects.

This means that you can use functions as data, which has the curious effect of reducing the need for variables that maintain state. If you find that yourself reaching for the var statement, or are using one or more "if" statements, then you're straying from a functional style.

Another notable idiosyncrasy of functional style is that functions should ONLY return the result of their evaluation and have no side effects on the state outside of their scope:

// oops, this is producing a side effect
function sideEffecter(){//theres no input...        
    window.thingy = 'foo';
    // hey, this isn't returning anything!!!
} 

Functional languages are non-destructive - meaning that they do not mutate the input, but rather return entirely new data based on the input. See this thread: https://stackoverflow.com/questions/749084/jquery-map-vs-each

Functional languages also feature a lot of methods in common - with names like "map", "fold", "reduce" that process lists/collections. In JS, unlike other languages, we have to handcrank these into existence - see libraries like underscore.js for some examples, although the latest implementation of JS has some of these straight out the box.

The important thing to bear in mind (IMO) is that while JS can utilise some functional patterns, it is not always well equipped to execute then.

Take iterating over an array, for example. You can do this using a functional style or the native loop constructs - and generally speaking the loop is more performant. Take this example - hit it with loops of increasing size and record the execution times in different browsers (i've done this already, but I've lost the benchmarks - sorry!):

var test = ['foo', 'bar', 'baz'], removeFunc, removeLoop;

//(semi)functional style...
// to be really functional each condition in the ternary would be another function
removeFunc = function(src, trg) {
    return src.length === 0 ? 
        src : 
            src[0] === trg ? 
                src.slice(1) : 
                    [src[0]].concat(removeFunc(src.slice(1), trg));
};

//but this is faster
removeLoop = function(src, trg){
    var len = src.length, // using variables to represent state...
        i=0, 
        result = [];        
    while(i < n){
       if(src[i] !== trg){
          result.push(src[i]);
       }
       i = i+1;
    }
}

In addition, if you use a functional construct to hit loops of considerable size and don't utilise some form of ad-hoc stack management you could flood the stack (although, to be fair, you need a BIG list for this to occur...). You've also got to factor in to the mix the variant optimisations in each browser - although if you're working in a Node.js environment this is obviously more of a fixed target.

That's not to say you shouldn't use functional constructs in Javascript - just be aware of the limitations in it's implementation relative to it's environment.

Here are some links that might be of interest to you:

A good chapter on Functional Programming in Javascript from the excellent "Eloquent Javascript"

The Little Schemer

a friend of mine wrote a JS library based on the Little Schemer

A good tutorial on Scheme that might help you better comprehend FP

sunwukung
  • 2.3k
  • 1
  • 17
  • 29