Basics of Functional Programming in JavaScript I
Musa Badru
I’ll be covering partial application, currying, compose, and pipe .These functional programming concepts that can significantly enhance code modularity and readability. Let’s delve into each of these concepts with code examples.
Partial Application:
Partial application involves fixing a specific number of arguments of a function and generating a new function with fewer arguments.
Example:
function add(x, y) {
return x + y;
}
// Partially apply the add function to fix the first argument
const add2 = add.bind(null, 2);
console.log(add2(3)); // Outputs: 5
Here, add2
is a partially applied function with the first argument fixed at 2.
Currying:
Currying is a technique where a function with multiple arguments is transformed into a series of unary (single-argument) functions.
Example:
function multiply(x) {
return function (y) {
return x * y;
};
}
const multiplyBy2 = multiply(2);
console.log(multiplyBy2(3)); // Outputs: 6
In this example, multiply
is a curried function that takes two arguments but is composed of two unary functions.
Compose:
The compose
function combines multiple functions from right to left, creating a new function that applies each function in succession.
Example:
function double(x) {
return x * 2;
}
function increment(x) {
return x + 1;
}
const doubleThenIncrement = compose(increment, double);
console.log(doubleThenIncrement(5)); // Outputs: 11
In this case, doubleThenIncrement
composes the increment
and double
functions.
Pipe:
Pipe
is similar to compose
, but it applies functions from left to right.
Example:
function triple(x) {
return x * 3;
}
function square(x) {
return x ** 2;
}
const tripleThenSquare = pipe(triple, square);
console.log(tripleThenSquare(4)); // Outputs: 144
tripleThenSquare
applies the triple
function first, followed by the square
function.
Use Cases:
-
Partial application and currying: These techniques are useful for creating specialized functions from more general ones, improving code reuse.
-
Compose and pipe: They help create function pipelines for data transformation, making code more readable and easier to reason about.
Implementing Compose and Pipe:
Here are simple implementations of compose
and pipe
functions:
function compose(...fns) {
return function (x) {
return fns.reduceRight((acc, fn) => fn(acc), x);
};
}
function pipe(...fns) {
return function (x) {
return fns.reduce((acc, fn) => fn(acc), x);
};
}
You can use these implementations to compose and pipe functions as demonstrated earlier.
Functional programming concepts like partial application, currying, compose, and pipe can make your code more modular, maintainable, and expressive. Understanding when and how to use these concepts is valuable for writing clean and functional JavaScript code.