Idiomatic and performant computed value? #48
-
First off, I really love the concept of ArrowJS. Basically I'm caught between React and Svelte. I love the functional nature of React, but dislike just about everything else about it. I like the simplified reactivity of Svelte, but dislike its templating. I was wondering if there was a good way to handle expensive computed values in ArrowJS. In React, there's But I'm not able to come up with anything satisfying in ArrowJS. It seems like I'd have to memoize a pure function and then create a wrapper function for use in templates that passes in all the reactive state needed to compute that value, but that's a little tedious. Granted, for as often as I have computationally expensive operations, maybe this isn't the end of the world. I could be missing something, though. It'd be nice if there was something akin to e.g. (not realistic or computationally expensive, but to demonstrate what I'm thinking) const state = reactive({
width: 1,
length: 2,
height: 3
})
// hypothetical memoize function, state.width and state.length tracked as dependencies
const getArea = memoize(() => state.width * state.length)
// Uses computed value itself, tracking its dependencies in addition to state.height
const getVolume = memoize(() => getArea() * state.height)
// no templates currently using area nor volume, so this shouldn't trigger any recomputations
state.width = 3
const someTemplate = html`The total volume is ${volume}`
// now a template is using volume, so this should recompute area and volume
state.width = 5
// this should recompute volume, but since no values of area have changed, area shouldn't recompute
state.height = 10 |
Beta Was this translation helpful? Give feedback.
Replies: 2 comments 1 reply
-
This is such a great question — I think I’m going to write a full article as a response to it :) |
Beta Was this translation helpful? Give feedback.
-
Let me give a couple of thoughts on this @duncsully. The first thing to know is that reactivity in Arrow is fine-grained (unlike React). It only recomputes and re-renders values when the used dependencies are modified. Now, that is not the same thing as memoization but in many instances, it results in roughly the same effect with no specific need for actual memoization. Idiomatically speaking, Arrow’s goal (and it is still exploration, we’re all learning here) is to solve the same problems as the more prominent frameworks using only this 2kb library to “shim” a declarative API. In that sense, Arrow is as much about the discovery of novel techniques as anything else. So for your specific code example, I would solve it like this: https://codepen.io/justin-schroeder/pen/BaOoqwa Now, to the memoization point, the above example is as efficient as possible except in one scenario — when changing the https://codepen.io/justin-schroeder/pen/bGxpmKP In this second example, we are using a watcher to create our memoized value in the If memoization was important for a given use case — this is how I would expect Arrow users to implement it. Now it would be trivial to wrap this into a composable “useMemo” like function, but personally, I think it is more transparent to store these values in plain sight of the usage. There is no new primitive here and no need to change mental models of the underlying data. Again, I don’t have all the answers here, and I’m very open to expanding my horizons, but what I’m most excited about with Arrow is having moments of discovery where we find these sorts of useful patterns hiding in plain sight. ❤️ |
Beta Was this translation helpful? Give feedback.
Let me give a couple of thoughts on this @duncsully. The first thing to know is that reactivity in Arrow is fine-grained (unlike React). It only recomputes and re-renders values when the used dependencies are modified. Now, that is not the same thing as memoization but in many instances, it results in roughly the same effect with no specific need for actual memoization. Idiomatically speaking, Arrow’s goal (and it is still exploration, we’re all learning here) is to solve the same problems as the more prominent frameworks using only this 2kb library to “shim” a declarative API. In that sense, Arrow is as much about the discovery of novel techniques as anything else. So for your specific c…