Any time you’re writing code, it means the code is going to be doing work for you. Many times, the burden of that work is transparent to us and our users. When it does make itself apparent, we have a performance issue on our hands. On the front-end this might manifest itself as lag or jank. On the back-end we may have higher latency or slow responses.
Sometimes there are ways of choosing faster algorithms or better data structures to resolve our performance issues, but not always. So what do we do when we’re too slow but can’t speed things up any more? One way of doing this in JavaScript is called memoization, which is a functional programming technique used to deal with costly pure functions.
With memoization, you “wrap” a function with another function that remembers the arguments and returns results of function calls. The result is essentially an in-memory cache that is transparent to your users. Let’s get a close look at memoization by implementing memoization around a simple but costly function.
A note on performance improvements: If you’re seriously looking at improving performance, the first step is to measure current performance. Without clear measurements, you won’t have any way of identifying your bottlenecks or validating candidate solutions. For the sake of this post, I’ve written a small function in JavaScript that takes a function and its arguments and times the execution of that function. It looks like this:
const timeFn = (fn, args = []) => {
const start = Date.now();
const returnValue = fn(...args);
const end = Date.now();
console.log(`Execution took ${end - start} ms`);
return returnValue;
}
The function we’ll use to test out memoization will add up numbers between zero and a number passed in as an argument. That function could be defined like this: