What are some situations for when we can use the `useCallback()` & `useMemo()` Hooks in React components?
Well, one case where we need `useCallback()` is when we call a helper function w/in `useEffect()`, so we need "referential equality" to include it in deps
/thread 🧵👇🏾
I also use `useCallback()` by default when returning a function from a custom Hook cuz I dunno how that function will be used w/in host components
`useCallback()` gives a stable function reference similar to the updater func from `useState()` (the 2nd array element)
🧵👇🏾
The `useMemo()` Hook is similar to `useCallback()` except that it memoizes any value not just functions
So I use `useMemo()` in the same situations: when I have a derived object/array that's used in the deps of `useEffect()`
(I like to think of "memoization" as a cache)
🧵👇🏾
The other major use case is to avoid expensive recalculations of derived data. Like if we're filtering an array of 1000+ items & the component is re-rendered many times/sec
But I've yet to need `useMemo()` for this purpose in the couple of years of using Hooks in React...
🧵👇🏾
By the way, I doubt this is how it’s actually implemented in React under the hood, but we can implement `useCallback()` with `useMemo()` 😉
Just a little nugget of information before you go 😄
🧵👇🏾
My latest post has more details in the examples showing when using the `useCallback()` & `useMemo()` React Hooks are helpful in reducing component re-renders
What other use cases do *you* use `useCallback()` or `useMemo()`?
Many people advise junior devs to dabble in several areas to get a breadth of knowledge but I think depth in a single area provides the best chance for growth early on
So I wrote up my suggested approach in a post last year
That's it for this week! If you wanna keep up with all my posts on React, TypeScript, DivOps & more, feel free to subscribe to the BenMVP Newsletter. It's got all the goodies!
The .reduce() method is maybe the most powerful, yet least understood array method. It basically allows us to transform an array into... nearly anything else
Let's re-implement 1️⃣0️⃣ lodash functions to learn more about how for examples on how .reduce works
/thread 👇🏾🧵
1️⃣ sum()
ℹ️ Computes the sum of the values in an array
The function is called a "reducer" & the 2nd param is our initial value
The 1st arg of the reducer is the "accumulator" (the value we're building up). The 2nd is the current array element in the iteration
/thread 👇🏾🧵
2️⃣ countBy()
ℹ️ Creates an object w/ keys that are the array elements and values that are their counts
Here we're turning an array into an object
(can't forget to return the object we're accumulating!)
Here is a quick React custom Hook that supports copying text to the system clipboard. It also returns a copied/failed status that can be reflected in the UI
(I remember the days when we could only do this w/ Flash 😭)
more details in the thread 🧵👇🏾
useCopyToClipboard returns a copy function that the UI calls when the user wants to copy the text (likely a button click). It updates the status based on the success/failure of writing to the clipboard
It uses useCallback to ensure a stable function reference
🧵👇🏾
It also uses useEffect to set a timeout that will reset the status after a specified amount of time. This basically makes the status fleeting, which is a typical user experience
Using objects/arrays in deps for React useEffect can cause it to run the effect on *every* re-render even if contents are the same cuz the references are different
We've got a couple of options...
1️⃣ Depend on the obj properties instead of the entire obj
/thread 🧵👇🏾
2️⃣ Duplicate the object within the effect when the *entire* object is needed. useEffect then depends on the pieces needed to create the object
In general creating object literals is cheap so the perf wins from optimized useEffect should outweigh the duplication
🧵👇🏾
3️⃣ Memoize/cache the object w/ useMemo Hook if creating the object is too expensive to do it twice. The obj is now safe to use in deps
This is suggested by the `react-hooks/exhaustive-deps` ESLint rule (part of `eslint-plugin-react-hooks` which you should totally be using)