What is the best way to apply function composition in JavaScript?

Here are three functions that can be combined to produce an output of 30:

const add = (a) => a + 10;
const mul = (a) => a * 10;
const divide = (a) => a / 5; 

// How would you write the `compositionFunction` to achieve this?
compositionFunction(add, mul, divide)(5);
//=> 30

The expected result is 30 because:

5 + 10 = 15
15 * 10 = 150
150 / 5 = 30

Answer №1

Here is an example

const sum = (a) =>  a + 10 ;
const product = (a) =>  a * 10 ;
const divideByFive = (a) => a / 5 ; 
// How to utilize these functions -----

const customFunction = (...f) => v => f.reduce((res, f) => f(res), v)

console.log(customComposeFn(sum, product, divideByFive)(5));

Answer №2

There are two types of function composition:

  1. Left-to-right function composition also known as pipe
  2. Right-to-left function composition also known as compose

Here is a fun recursive approach to implementation:
This assumes there are at least two functions to combine

const compose = (...fn) => {
  const [[f, g], x] = [fn.slice(-2), fn.slice(0, -2)];
  const h = a => f(g(a));
  return x.length ? compose(...x, h) : h;
}

const pipe = (...fn) => {
  const [f, g, ...x] = fn;
  const h = a => g(f(a));
  return x.length ? pipe(h, ...x) : h;
}

Let's test it out:

const foo = x => x + 'foo';
const bar = x => x + 'bar';
const baz = x => x + 'baz';

pipe(foo, bar, baz)('');
//=> 'foobarbaz'

compose(foo, bar, baz)('');
//=> 'bazbarfoo'

Answer №3

const add = (num) => num + 10;
const multiply = (num) => num * 10;
const divideByFive = (num) => num / 5;
const customFunction = (...functions) => {
    return function (argument) {
        if (functions.length > 0) {
            const output = functions[0](argument);
            return customFunction(...functions.splice(1))(output);
        } else {
            return argument;
        }
    };
};
const result = customFunction(add, multiply, divideByFive)(5);
console.log(`result`, result);

Answer №4

My approach would be the following:

function combineFunctions(...functions) {
  return function(input) {
    let func, result = input;
    while (func = functions.shift()) {
      result = func(result);
    }
    return result;
  }
}

const reduceByOne = num => num - 1;
const multiplyByTwo = num => num * 2;
const divideByThree = num => num / 3;
// Usage example -----
console.log(combineFunctions(reduceByOne, multiplyByTwo, divideByThree)(12));

Similar questions

If you have not found the answer to your question or you are interested in this topic, then look at other similar questions below or use the search

Only first-level items are listed here

I need to add an icon inside the <li> tag if that element contains another nested list (<ul>). HTML <ul> <li><a href="#">link</a></li> <li><a href="#">link</a> <ul> ...

Is there a way to provide a dynamic value for the p:remoteCommand ajax call?

My issue involves a p:dataTable that contains p:commandLink elements. I need to initiate an ajax call with parameters when the mouseover event occurs. After some research, it became clear that commandLink cannot trigger an ajax call on mouseover directly - ...

Extracting the video identifier from YouTube's embed code

I'm currently in the process of converting a PHP preg_match expression to extract a video ID from YouTube embed code using JavaScript. Here's what I have in PHP: $pattern = '%(?:https?://)?(?:www\.)?(?:youtu\.be/| youtube\.co ...

What are the steps to design a versatile gallery page that can serve various projects?

Allow me to get straight to the point. What is my goal? I am aiming to develop galleries for various projects. Each project's thumbnail on the main page should open a gallery as a new page. These galleries will all have the same layout but different ...

step-by-step guide on implementing autocomplete using google.maps.places.autocomplete in ExtJS

Just to clarify... I initially wrote a code that was error-free before editing this post. However, after reading a comment on creating a Minimal, Complete, and Verifiable example, I became confused. My minimal script did not work properly, I couldn't ...

Not quite sure about the best way to showcase the results // using JavaScript

My code is posted below. I am trying to achieve a functionality where, upon clicking the 'Calculate Price' button, the results showing the number of cars, type of cars, and their respective prices are displayed beneath the button. Despite this be ...

tables that are intertwined

There are three tables on my page and they are all overlapping. Is there a way to prevent this overlap? Check out this link <table id="inventoryTable" class="table dataTable" aria-describedby="inventoryTable_info"> <thead& ...

Cloning a file input does not retain the uploaded file in the cloned input. Only the original input retains the uploaded file

Whenever I duplicate an input type file, I encounter an issue where the uploaded file from the duplicated input is also linked to the original input. It seems like the duplicate input is somehow connected to and taking files for the original one. This is ...

Tips for fully accessing a website with javascript enabled through an android service

I've been attempting to extract data from a website node that includes JavaScript. In VB .NET, the code I typically use is as follows: Dim listSpan As IHTMLElementCollection = bodyel.getElementsByTagName("span") For Each spanItem As IHTMLElement In ...

What is the method for obtaining the number of weeks since the epoch? Is it possible to

Currently, I am setting up a DynamoDb store for weekly reporting. My idea is to use the week number since 1970 as a unique identifier for each report record, similar to epoch milliseconds. Here are some questions I have: How can I determine the current w ...

Exploring the fundamentals of authentication with Express JS

Currently, I am encountering a challenge while attempting to implement basic authentication with Username and Password using Express JS. The problem lies in the fact that when I try to incorporate an if statement within an app.use() function, it does not s ...

DirectUpload is failing to trigger directUploadWillStoreFileWithXHR for file storage

I have implemented Rails ActiveStorage on an ECS class import { DirectUpload } from "@rails/activestorage"; function createDirectUpload(file, source, controller) { return new DirectUpload(file, source.url, source.token, source.attachmentName, ...

I can't figure out why I'm receiving a TypeError stating that onSuccess is not a function within my AngularJS service

Utilizing an angularjs service that utilizes restangular for API calls. angular.module('app.userService', []) .factory('userService', ['localStorageService', '$rootScope', 'Restangular', func ...

Exploring the capabilities of JavaScript on the iOS platform

Here is the code I've written for my iOS application: webView = [[UIWebView alloc] init]; webView.delegate = self; [webView loadHTMLString:@"<script type=\"text/javascript\" src=\"myFile.js\"></script& ...

Is there a way to extract information from an HttpClient Rest Api through interpolation?

I am currently facing an issue with a component in my project. The component is responsible for fetching data from a REST API using the HttpClient, and the data retrieval seems to be working fine as I can see the data being logged in the Console. However, ...

What causes the discrepancy in margin values between desktop and mobile devices?

In my project, I have a collection of div elements that need to be spaced vertically from one another by the height of the window plus an additional 100px. However, I encountered a discrepancy when setting this margin using jQuery between mobile and deskto ...

Why is my PHP function not able to properly receive the array that was sent to it via Ajax?

After retrieving an array through an ajax query, I am looking to pass it to a PHP function for manipulation and utilization of the elements at each index. The PHP function in question is as follows: class ControladorCompraEfectivoYTarjeta { public fu ...

Utilizing the keyword 'this' within a function of a JavaScript class that is invoked with the .map method

I am working with the RegisterUser class which contains various methods and properties: class RegisterUser { constructor(username, password, ispublic){ this.username = username; this.password = password; this.ispublic = ispublic; this.id ...

Internet Explorer (on mobile devices) does not display submenus when touched

Hello, I have a query about displaying a sublist on touch. I have created a sublist that is supposed to show up when you hover over it. You can view the demo here: @import url(//fonts.googleapis.com/css?family=Titillium+Web:400,200,300,600,700); body { ...

Retrieve the base64 encoded data from localStorage and showcase it within a div element

After researching a similar question about checking for the existence of a localStorage variable and setting an else if function, and also looking into how to load a base64 image and display it on a div, I have come up with the following code: HTML: <i ...