Transducer
A transducer is a function which takes in a reducer, and returns another reducer
- A transducer takes an object or array, iterating through each value, transforming each element with a composition of transformer functions
The transduce function is really just a reduce function with an additional argument upfront:
// With reduce
R.reduce(R.flip(R.append), [], autobots)
// With transduce
R.transduce(transform, R.flip(R.append), [], autobots)
the above reduce function iterates the elements of our autobots
array and appends them to the accumulator
When we use transduce()
, we are passing each item from our list into our transformation function before passing it to our reducing function. So basically, transduce is just a way for us to transform items while reducing them. We are, in fact, transducing
transducers are a generic and composable way to operate on a collection of values, producing a new value or new collection of new values
In this example, we can see the power of transduce
. The first way, we need to iterate over autobots
a total of 3 times. However, when we use transduce
as in the second way, we only need to iterate over it once.
- The traditional way, is that we perform
map
on each element of the array, thenmap
on each element again, thenfilter
on each element. With transduce, we performmap
on the first element, thenmap
again on the first element, thenfilter
on the first element. The resulting value is then mapped to the output array, then the second element is performed on.
let autobots = ['Optimus Prime','Bumblebee','Ironhide','Sunstreaker','Ratchet']
// Filter for autobots that contain 'r', uppercase, then reverse
let transform = R.compose(
R.filter(x => /r/i.test(x)),
R.map(R.toUpper),
R.map(R.reverse)
)
// BEFORE
transform(autobots)
// => [ 'EMIRP SUMITPO', 'EDIHNORI', 'REKAERTSNUS', 'TEHCTAR' ]
// AFTER
R.transduce(transform, R.flip(R.append), [], autobots)
// => [ 'EMIRP SUMITPO', 'EDIHNORI', 'REKAERTSNUS', 'TEHCTAR' ]
The word ‘transducer’ itself can be split into two parts that reflect this definition:
transform
— to produce some value from another (ex.reduce
/map
).reducer
— to combine the values of a data structure to produce a new one.- this is a really cool concept, because it allows us to abstract away any implementation detais that we
.map
and .filter
can be implemented with .reduce
. Therefore, we see that .reduce
is a more general function, and .map
and .filter
are more specific implementations of .reduce
. Transduce allows us to treat a reduce-like construct as a higher order function, meaning we can pass in the reducing function (which is the function found in a reducer)
- This means we could create
.map
/.filter
with a transducer more info