7 ms·
(I'm on the ReactJS team at Facebook) >> pathological case for something like React. The is absolutely likely to be the case (for now). I admit I haven't look
by jordwalke 12y ago
(I'm on the ReactJS team at Facebook)
>> pathological case for something like React.
The is absolutely likely to be the case (for now). I admit I haven't looked into the technical issues very much because I've been spending 100% my time on ReactNative which seeks to resolve the deepest issues with the browser environment for React development - it's certainly a different kind of performance work.
For this kind of stuff, most people create a highly custom React base class that "cuts right to the chase" as far as updating small pieces that change in large lists. Immutable data structures are often the most helpful tool in accomplishing that. I'm sure they have totally legitimate reasons to go with this approach in the mean time, and most of all I want their project Atom to succeed because it's such a great idea. I hope we can help the Atom team soon to resolve these other issues though.
- seanmcdirmid 12y ago> Immutable data structures are often the most helpful tool in accomplishing that. This is said often but without much qualification. I've found mutable data structures with change propagation (via observable or what not) to work much better given that the whole diffing thing can be avoided altogether since you know exactly what has changed. It is my understanding that the DOM is broken in how it handles invalidation/re-rendering (doing it for each modification rather than batching), but again, I don't see how immutability helps fix that problem any better than just doing it the right way with a mutable virtual DOM?
- vjeux 12y agoHighly recommend watching Lee Byron talk about immutability. He covers your doubts very well. http://conf.reactjs.com/schedule.html#immutable-data-and-react http://conf.reactjs.com/schedule.html#immutable-data-and-rea...
- seanmcdirmid 12y ago> Immutable data unlocks powerful memoization techniques and prohibits accidental coupling via shared mutable state. Memoization is still more expensive than just tracking changes and avoiding unnecessary recomputations directly (it only starts winning when doing dynamic programming). There is a point on accidental coupling but this is more of a correctness rather than performance issue. In the high-performance computing field, use of immutable data structures is suicidal; even tries are a magnitude slower than in-place mutable data structures. And he only compares against naked shared mutable state, not against managed mutable state with change propagation. And that gets to the end of the talk: the real reason is they want to avoid using frameworks that already solve this problem by tracking changes, and React somehow avoids that since you can do just the diff post facto. Ok, I get that.
- moomin 12y agoYes, but immutability means that reference checks are enough to spot unchanged areas. And we're not in HPC land right now, we're writing JavaScript. In that world, Om (immutable) is vastly faster than Backbone, Knockout, Angular, Ember &c (mutable). Partially because, when you can reason more clearly, it's easier to do something about the performance.
- seanmcdirmid 12y agoReference checks are conservative in spotting unchanged areas (if true, definitely no change, if false, maybe no change) unless all values are internalized (a bit expensive to do that). Also, diffing is only needed at all when you need to compare values anyways; dirty bits are otherwise sufficient to mark changes. I'm not really familiar with the web ecosystem, but why would it differ so much from say C#/WPF? or a system based on change propagation instead of diffing?
- joewood1972 12y agoIf everything is immutable then a reference check is all you need. They key is to avoid deep copies. Observables are problematic when changes can ripple through your model/view-model - resulting in multiple DOM changes. This equally applies to WPF.
- seanmcdirmid 12y agoWPF has a retained scene graph, so no diffs are necessary, all changes are just O(1). Reference equalities only work to know what really hasn't changed, they of course can't tell you that two values are still equal even if their references are different (unless compketely internalized, of course). For react, that's fine: it's just some extra work if false inequality is encountered, there are other applications where its not ok.
- jordwalke 12y agoMost of the people that don't believe that immutable, persistent data structures are effective tools to increase performance of reconciliation, only put one foot in (that's my personal experience). That kind of reservation often compels people to "just try immutability on a part of their tree". It doesn't work like that and you often should go all in before you begin seeing the benefits. It's a leap of faith, admittedly. Almost every application (ever) is a list of lists of lists (and so on). Even text can be broken up into paragraphs/code-blocks etc which form the lists. If these structures form a tree, and that tree is somewhat well balanced, then small changes can be found in log(n) time by comparing reference identity without developer intervention (by either a mixin or Om-like system). log(n) ends up being extremely fast for n in the range of graphical nodes in most UI applications. For everything else, a windowing infrastructure can be used (usually baked into a very sophisticated <ListView> component - our ReactNative mobile applications use this approach (special <ListView> component that exploits immutability without developer intervention)).
- seanmcdirmid 12y agoThanks for your reply! I work in this field and have written lots of code, both mutable and immutable, declarative, OO and functional, to solve a variety UI problems. I've also written my own language-enabled editors using multiple techniques (see comment https://news.ycombinator.com/item?id=9117234 https://news.ycombinator.com/item?id=9117234 for the one I'm working on right now, but you can see https://www.youtube.com/watch?v=SAoRWmjl1i4 https://www.youtube.com/watch?v=SAoRWmjl1i4 for an Eclipse-based one I did in 2007), so I've definitely got multiple feet in the game. I don't work in Web, most of my UI code was written for Swing, SWT (Eclipse), and these days WPF in immediate mode. It seems like React is solving a bunch of JS/DOM problems, so maybe my experience doesn't transfer, but I've found that for my work, it is much easier to just go with mutable data structures that support change propagation, so you make a change that affects a line in a block (my current editor architecture, block - lines - more blocks - more lines - etc...), the change is just...O(1) because the line can be damaged/repaired directly! So why would I give that up for O(log(n))?
- jordwalke 12y ago
- Skinney 12y ago> This is said often but without much qualification. I've found mutable data structures with change propagation (via observable or what not) to work much better given that the whole diffing thing can be avoided altogether since you know exactly what has changed. The problem with this though, is that the entire framework would have to be written around this idea, and everyone who uses the framework would have to use these datastructures correctly. That being said, it will probably be both more efficient and relatively easy to use once Object.observe lands in Ecmascript 7. In the meantime React works with every datastructure out there, which is a big plus. Immutable datastructures, while more expensive to change, could be very cheap to diff, because you know if two objects have the same pointer, they're equal.
- seanmcdirmid 12y ago> The problem with this though, is that the entire framework would have to be written around this idea, and everyone who uses the framework would have to use these datastructures correctly. That is the problem, and one of the reasons why I haven't ported Glitch (works in C#) to Javascript yet (instead, opting to wrap it up in a new language). > Immutable datastructures, while more expensive to change, could be very cheap to diff, because you know if two objects have the same pointer, they're equal. Yes, I use this property a lot in my own code; I'm pragmatic and use both mutable/immutable data structures. That being said, I find it easy to trace changes and do change propagation on a mutable data structure (that can change) vs. an immutable one (which obviously require diffing since you can't know exactly what changed). Using immutable data structures actually make that problem much harder from my point of view, but I see its utility as an easy way to integrate with existing code and programming practices (something I can't offer).
- antihero 12y agoThe true speed of using an immutable library for your data in React comes from shouldComponentUpdate. Using immutable structures is really fast as the most deepest comparisons are always O(1) because all you're doing is comparing memory addresses, thus a component can very cheaply work out whether the data given to them has changed, and as little as possible can be recalculated.
- crazychrome 12y agoOne question: when can we have a real look at react-native ?