JSFiddle - React, Tailwind, and code Playground

JavaScript

const compose = (...fns) => fns.reduce((f, g) => (...args) => f(g(...args)))
const add = x => y => x + y
const multiply = x => y => x * y
const multiply3 = multiply(3);
const add2 = add(2);
const add2Multiply3 = n => multiply(3)(add(2)(n))
const composeadd2Multiple3 = compose(add(2), multiply(3));
//the above is simplified from passing in an input as compose automatically passes the input: 
//const composeadd2Multiple3 = (input) => compose(multiply(3), add(2))(input);

//or could call immediately passing value 2:
//compose(multiply(3), add(2))(2)
console.log(add2Multiply3(2));
console.log(composeadd2Multiple3(2));


const map = func => (...args) => (console.log('args',args), args.map(func))
const join = strings => strings.join('')
const processHello = d => console.log(d);
map(processHello)('Hello','Hello world','Hi');
const processEachHello = map(processHello);
processEachHello('Hello','Hello world','Hi');

console.log('check map')
console.log(map(x => x + '!')('hi','you'))
console.log(join(['hi','you']))

const mapBangJoin = compose(join, map(x => x + '!'));

console.log(compose(join, map(x => x + '!'))('hi', 'you'));
console.log(mapBangJoin('hi', 'you'));

/*
function composition steps:
- break up the work into functions that take as their last argument the actual "data" they should work on, this means if the function takes multiple arguments, then curry the function such that the last function argument is the data.
  > each curried argument should be an essential required part of the function, ie. it's no use creating a html tag function that takes arguments: tagName => attrs => content
- use the compose to compose these functions calling functions together such that the only argument to this call is the data. 
*/