Intuitive Transducer in JavaScript

Image for post
Image for post

It’s been about two month since Kyle Simpson (getify) gave a JavaScript workshop at trivago. I had so much fun though out the week and I really enjoyed it with Kyle’s story telling and reasoning behind the materials.

I missed the last day of the workshop about functional programming so I decided to visit the material on Frontend Masters last night. He ended the course with a notion of transducing and I thought to myself

Maybe I’ll try to explain it with my own take.

So here we go.

What is transducing? Simply put, it’s a data transformation process without creating intermediate products. It’s like a pipeline. It’s your data on one end, and the pipeline transforms the data and produce your output on the other end.

Let’s say we have a set of data, and I’m using the example from Kyle’s example from the course so we have a reference to understand the concept better:

and the transformation we’d like to perform is to output the sum of the data after incrementing one on each entry and then filtering out the even entries.

For each operation on the list, we produce a new list. And the new lists are the intermediate products. Transducing is a technique to avoid the intermediates and get that output straight out of one transformation. like this

So how do we do that? We connect the operations together by making the operations share the same shape of input and output.

Since we are reducing our list into a single number, let try to refactor our example to chain reduces.

Now if we look at the mapAddOneReducer , the incrementing responsibility is actually entangled in the function. We could extract it from mapAddOneReduce so we have function and all it does is to increment one. So let’s separate them.

Same for filterIsOddReducer , let’s separate the predicate that determines whether a number is odd from the reducer.

So the example becomes like this

Much cleaner and the concerns are separated! But here are more separations we can do on mapReducer and filterReducer, right? Reducing is entangled with mapping and filtering! Let’s remove that itchiness.

So now we can pass in a reducer to tell mapper and filterer how to reduce.

Now that we have a clear separation of concerns and we can see how similar mapper and filterer is. They both have the same input type and output type now. They both take in a function and produce a function that takes in a reducer and returns a reducer. So we can compose them like this.

We can go one step further to properly compose the mapper and filterer.

We are so close to come up with a one-stop shop to transform the data! Let’s analyze transformation for a second.

Our current strategy is to generate a new list with transformer and then sum it up. The new list is a intermediate product that we want to avoid from the process. Now, instead of generating a new array and sum from it, why don’t we sum every step of the way while going through the list after transforming?

or

We did it! We have a single transformation to get the output that we are looking for. We have one reduce operation and get the output straight out of it without producing any product on the way. And that single transformation transformer(sum) is our transducer!

or to be more clear

Here you have it!

The whole process of finding the transducer is a little bizarre, but it actually makes sense if you look at it as a mathematical process. We are doing the same thing as we are handling algebra expressions. We break down the expression, find patterns, and reconstruct the expression to formulate the solution. It’s quite cool that we’re able to do that with JavaScript, right?

Any thought about functional programming and transducers? Drop me a comment or find me on twitter!

Write for developers. Documenting web technology, coding patterns, and best practices from my learnings. Software engineer @trivago.

Get the Medium app

A button that says 'Download on the App Store', and if clicked it will lead you to the iOS App store
A button that says 'Get it on, Google Play', and if clicked it will lead you to the Google Play store