在Ramda管道中使用相同的第一个参数

时间:2016-08-02 04:26:08

标签: javascript ramda.js

是否可以在Ramda组成以下功能?

(a, b) => R.pipe(func1(a), func2(a))(b)

目标是将参数a传递给pipe

中的所有函数

我最初的想法如下:

R.pipe(R.juxt([func1, func2]), R.apply(R.pipe))

但这会给TypeError: Cannot read property 'length' of undefined

2 个答案:

答案 0 :(得分:1)

使用S.pipe更容易表达,因为它需要数组函数来组合。

一种选择是使用R.ap

> S.pipe(R.ap([S.add, S.mult, S.add], [3]), 10)
42

另一个选择是使用R.map和鹅口疮组合S.T

> S.pipe(R.map(S.T(3), [S.add, S.mult, S.add]), 10)
42

然后您可以将其中一个包装在lambda中以创建二进制函数:

const f = (a, b) => S.pipe(R.ap([S.add, S.mult, S.add], [a]), b);

f(3, 10);  // add(3)(mult(3)(add(3)(10)))
// => 42

答案 1 :(得分:0)

您必须创建所有函数的curried版本,然后使用a调用每个函数的curried版本,最后在bR.pipe <中使用R.reduce / p>

假设需要a作为第一个参数的函数是f,g,h(按特定顺序),那么我们想要实现以下表达式

h(a, g(a, f(a, b)))

首先让我们创建一个curried函数,它接收两个参数,一个值v和一个函数fn,当这个函数收到它所需的所有参数时,它只返回fn(v)

const rev = R.curry((v, fn) => fn(v))

接下来,我们可以使用R.mapR.curry

创建函数的curried版本
// note the reversed order of the functions
// I'll use R.compose instead of R.pipe
let curriedVersion = R.map(R.curry, [h,g,f]) 

但是我们还需要使用a作为curried函数的第一个参数,我们可以使用a使用R.map调用每个curried函数,但我们将使用我们的特殊函数{ {1}}

rev

最后让我们使用const curriedVersion = R.map(R.compose(rev(a), R.curry), [h,g,f]) R.compose

这一系列的curried函数
b

一个班轮(对于特定顺序的函数const result = R.compose.apply(undefined, curriedVersion)(b) ):

f,g,h

const solver = (a, b) => R.compose.apply(undefined, R.map(R.compose(rev(a), R.curry), [h,g,f]))(b)
const add = (a, b) => a + b
const sub = (a, b) => a - b
const mul = (a, b) => a * b

const rev = R.curry((v, fn) => fn(v))
const solver = (a, b) => R.compose.apply(undefined, R.map(R.compose(rev(a), R.curry), [mul,sub,add]))(b)

// mul(2, sub(2, add(2, 3)))
// mul(2, sub(2, 5))
// mul(2, -3)
// -6
console.log(solver(2, 3))