Fundamentals 18 min read

Functional Programming in JavaScript: Concepts, Techniques, and Practical Applications

This article introduces functional programming as a programming paradigm, explains its core concepts such as pure functions, higher‑order functions, closures, currying, and functors, and demonstrates how these ideas are applied in modern JavaScript frameworks and libraries with clear code examples.

政采云技术
政采云技术
政采云技术
Functional Programming in JavaScript: Concepts, Techniques, and Practical Applications

Introduction

With the rapid evolution of the front‑end ecosystem, frameworks, syntax proposals and APIs change frequently, but the underlying programming ideas remain stable. JavaScript’s object‑oriented features can be cumbersome, so functional programming offers a more approachable alternative.

What Is Functional Programming?

Functional programming (FP) is one of several programming paradigms, alongside procedural, behavioral and object‑oriented programming. A paradigm can be seen as a mindset plus its implementation method.

Procedural programming : implement a task step by step.

Behavioral programming : flatten computation into a series of transformations, avoiding explicit instructions and object stacking.

Object‑oriented programming : model real‑world entities as classes and objects, using encapsulation, inheritance and polymorphism.

Functional programming : abstract real‑world entities and their relationships into pure mathematical mappings.

In FP, a function is a mathematical mapping from inputs to outputs, not merely a language construct. A pure function always yields the same output for the same input and has no side effects.

Basic FP Concepts

Example: computing the hypotenuse of a right triangle.

y = \sqrt{a^{2}+b^{2}}

Non‑functional implementation:

// non‑functional y = (a^2 + b^2)^0.5
const a = 3;
const b = 4;
const y = Math.sqrt(a*a + b*b);

// functional y = f(a, b)
const f = (a, b) => {
  return Math.sqrt(a * a + b * b);
};
const y = f(3, 4);

Higher‑Order Functions

"A function that takes another function as an argument or returns a function. To fully understand this, you must first know first‑class functions."

First‑class functions mean that functions are objects that can be assigned to variables, passed as arguments, and returned.

Example of a higher‑order function that processes an array:

const use = (arr, fn) => {
  return arr.map(i => fn(i));
};

Closures

"A closure binds a function together with its lexical environment."
function once(fn) {
  let done = false;
  return function() {
    if (!done) {
      done = true;
      fn.apply(this, arguments);
    }
  };
}
const logOnce = once(console.log);
logOnce(1);
logOnce(1);

Closures keep referenced variables alive on the heap after the outer function finishes, allowing inner functions to access them.

Pure Functions

"Same input yields same output without observable side effects."
let numberArr = [1,2,3,4,5];
// pure
numberArr.slice(0,2); // [1,2]
// impure
numberArr.splice(0,2); // modifies the original array

Pure functions enable caching, easier testing, and safe execution in multi‑threaded environments such as Web Workers.

Currying

Currying transforms a multi‑parameter function into a sequence of single‑parameter functions.

function checkAge(min) {
  return function(age) {
    return age > min;
  };
}
const checkAge18 = checkAge(18);
checkAge18(lucy.age);

FP with Lodash

Lodash’s fp module provides immutable, auto‑curried, iteratee‑first, data‑last utilities.

import _ from 'lodash';
const str = "CAN YOU FEEL MY WORLD";
const split = _.curry((sep, str) => _.split(str, sep));
const join = _.curry((sep, arr) => _.join(arr, sep));
const map = _.curry((fn, arr) => _.map(arr, fn));
const f = _.flow(split(' '), map(_.toLower), join('-'));
// f(str) => 'can-you-feel-my-world'

Using the fp variant:

import fp from 'lodash/fp';
const f = fp.flow(fp.split(' '), fp.map(fp.toLower), fp.join('-'));
// f(str) => 'can-you-feel-my-world'

Function Composition

Composition combines functions from right to left, turning nested calls into a pipeline.

function compose(...args) {
  return function(value) {
    return args.reverse().reduce((acc, fn) => fn(acc), value);
  };
}
// ES6 version
const compose = (...args) => value => args.reverse().reduce((acc, fn) => fn(acc), value);

Functors

A functor is a container that implements a map method to apply a pure function to its value.

class Container {
  constructor(value) { this._value = value; }
  map(fn) { return new Container(fn(this._value)); }
}
new Container(1).map(x => x + 1).map(x => x * x);

Using a static of method to hide the new keyword:

class Container {
  static of(value) { return new Container(value); }
  constructor(value) { this._value = value; }
  map(fn) { return new Container(fn(this._value)); }
}
Container.of(1).map(x => x + 1).map(x => x * x);

Advanced functors such as maybe , Either , IO , Task , and Monad address null handling, error handling, side‑effects, async execution, and nested IO respectively.

FP in Mainstream Frameworks

Redux middleware can be written in a curried style:

const middleware = store => next => action => {
  // implementation
};
// Equivalent flat signature
(store, next, action) => { ... };

React 16.8 introduced Hooks, which align well with FP principles: each hook is an independent, pure function, avoiding the “onion‑layer” complexity of higher‑order components.

class Example extends Component {
  componentDidMount() {
    // register events, request API, set state, etc.
  }
  componentWillUnmount() {
    // clean up listeners
  }
}

Using useEffect replaces lifecycle methods, making component logic more declarative and composable.

Conclusion

Functional programming is a paradigm that offers higher composability, flexibility, and fault tolerance. While it may not replace all existing patterns, it serves as a valuable supplement to reduce stateful complexity in JavaScript applications. Modern libraries such as React, RxJS and Redux embody many FP ideas, helping developers write more predictable and maintainable code.

References

Early history of functional programming (https://zhuanlan.zhihu.com/p/24648375)

Lodash FP Guide (https://github.com/lodash/lodash/wiki/FP-Guide)

Functional Programming Introduction (http://www.ruanyifeng.com/blog/2012/04/functional_programming.html)

Functional Programming – Functors (https://segmentfault.com/a/1190000023744960)

frontendJavaScriptFunctional ProgrammingHigher-order FunctionsCurryingpure functionsLodash
政采云技术
Written by

政采云技术

ZCY Technology Team (Zero), based in Hangzhou, is a growth-oriented team passionate about technology and craftsmanship. With around 500 members, we are building comprehensive engineering, project management, and talent development systems. We are committed to innovation and creating a cloud service ecosystem for government and enterprise procurement. We look forward to your joining us.

0 followers
Reader feedback

How this landed with the community

login Sign in to like

Rate this article

Was this worth your time?

Sign in to rate
Discussion

0 Comments

Thoughtful readers leave field notes, pushback, and hard-won operational detail here.