ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

自顶而下学习react源码 (1) 理念篇

2022-02-03 13:30:20  阅读:173  来源: 互联网

标签:渲染 中断 自顶 更新 react 源码 Renderer 组件 Reconciler


理念篇

  • 快速响应的瓶颈之一就是cpu限制,浏览器的js线程与gui渲染线程互斥,一旦js执行过长,就会导致卡顿。

​ 解决这个问题的关键就是:在浏览器每一帧的时间中,预留一些时间给JS线程,React利用这部分时间更新组件

​ 解决CPU瓶颈的关键是实现时间切片,而时间切片的关键是:将同步的更新变为可中断的异步更新。

  • 瓶颈之二就是IO的瓶颈: React实现了[Suspense ]功能及配套的hook——useDeferredValue为了支持这些特性,同样需要将同步的更新变为可中断的异步更新

老的react架构

分为两层:Reconciler(协调器)—— 负责找出变化的组件. Renderer(渲染器)—— 负责将变化的组件渲染到页面上

当有更新变化的时候,Reconclier会调用函数组件或者类组件的render方法,得到虚拟dom,然后进行diff算法比对,将变化的虚拟dom叫个Renderer渲染到页面上。

该架构的缺点:在Reconciler中,mount组件调用mountComponent方法,而update组件调用updateComponent方法,两个方法都会递归更新子组件,一旦开始,无法中断,当层级很深的时候,就会超过16ms,导致卡顿。react15的架构支持中断异步更新吗?

答案是否定的:老的架构,Reconciler和Renderer阶段是交替工作的,当有一处变化的时候,Reconciler比对完变化就立马给到Renderer去渲染,然后再继续寻找变化,如果中途断掉的话,这样就会导致用户可能会看到渲染不完全的ui。

新的react架构

react16的架构分为三层:

  • Scheduler(调度器)—— 调度任务的优先级,高优任务优先进入Reconciler
  • Reconciler(协调器)—— 负责找出变化的组件
  • Renderer(渲染器)—— 负责将变化的组件渲染到页面上
scheduler

react16新增了一个调度器scheduler,因为需要以浏览器是否有剩余时间作为任务中断的标准,需要一种机制,当浏览器有剩余时间的时候通知我们。比如部分浏览器实现的requeistIdleCallback,但是因为浏览器兼容性和触发频率的不稳定性,react实现了功能更加完备的requestIdleCallbackpolyfill,就是S cheduler,除了能在浏览器空闲时出发回调,还可以提供多种任务调度的功能。

Reconciler

react15中·,Reconciler是递归处理虚拟do m的,而react16的Reconciler,从递归变成了可以中断的循环过程,每次循环都会调用shouldYeild判断当前是否有剩余时间,再决定是否继续处理j s。

/** @noinline */
function workLoopConcurrent() {
  // Perform work until Scheduler asks us to yield
  while (workInProgress !== null && !shouldYield()) {
    workInProgress = performUnitOfWork(workInProgress);
  }
}

并且为了解决中断更新渲染不完全的问题,Reconciler和Renderer不再交替工作,而是当Schedule将任务交给Reconciler后,Reconciler处理所有fiber,将变化的fiber打上effectTag标记,只有所有的组件都完成了Reconciler工作,才会统一交给Renderer。

Schedule和Reconciler的工作是在内存中完成的,是可以中断(当前帧没有剩余时间,或者有其他更高优先级任务需要更新)的,用户并没有体验,而Renderer阶段是不可以中断的,如果中断会导致页面渲染不完整。

简而言之,15的Reconciler和Renderer是交替进行的,中断会导致不完全的ui,而react16在所有的组件完成Reconciler阶段,才统一交给R enderer阶段去渲染,所以这中间,Reconciler是可以因为某些原因中断的。

FIber

虚拟Dom无法满足可中断的异步更新需求。Fiber应运而生,作为架构,Recocniler基于Fiber节点实现,称为Fiber Reconciler,而作为静态的数据结构,fiber对应每一个React element,保存了组件的类型,对应的dom信息,相当于对应每一个虚拟dom。作为动态的工作单元,每个fiber节点保存了本次更新中组件的状态。

学习文章地址:https://react.iamkasong.com/

标签:渲染,中断,自顶,更新,react,源码,Renderer,组件,Reconciler
来源: https://blog.csdn.net/lin_fightin/article/details/122775433

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有