说说React render方法的作用原理?

最近使用react的比较多,记录一下一些react的面试题及自己的一些理解和补充,整理成文章更有助于梳理每个知识点的脉络。

Render的形式

在React中,render函数有两种形式:

  1. Class 组件 : 在类组件中,render方法是必需的。这个方法返回一个React元素,描述了组件在特定时间点应该渲染出的内容。例如:

    js 复制代码
    import React, { Component } from 'react';
    
    class MyComponent extends Component {
      render() {
        return <div>Hello, World!</div>;
      }
    }
  2. 函数组件 : 在函数组件中,render函数是函数本身。它接受props作为参数,并返回一个React元素。这个函数被调用时,会根据传入的props和组件内部的逻辑来决定要渲染的内容。例如:

    js 复制代码
    import React from 'react';
    
    function MyComponent(props) {
      return <div>Hello, {props.name}!</div>;
    }

render的原理

创建React元素树

在React应用中,开发者使用JSX语法编写组件的UI结构。当调用render方法时,React会将JSX转换为虚拟DOM(Virtual DOM)元素树

Render主要是把我们编写的jsx通过babel编译后就会转化成我们熟悉的js格式,比如下面这个代码:

javascript 复制代码
return (
  <div className='uname'>
    <Header> hello </Header>
    <div> world </div>
    Hello World
  </div>
)

babel编译后:

kotlin 复制代码
return (
  React.createElement(
    'div',
    {
      className : 'uname'
    },
    React.createElement(
      Header,
      null,
      'hello'
    ),
    React.createElement(
      'div',
      null,
      'world'
    ),
    'hello world'
  )
)

babel对render中的节点转换为虚拟节点,这些虚拟DOM树最终会渲染成真实DOM

比较虚拟DOM

在进行初次渲染或更新时,React会比较前后两次渲染的虚拟DOM树的差异。。React使用一种高效的算法来比较两棵虚拟DOM树的差异,并找出需要更新的部分。一般采用的是diff算法

生成DOM更新操作

js 复制代码
return (
  React.createElement(
    'div',
    {
      className : 'uname'
    },
    React.createElement(
      Header,
      null,
      'hello'
    ),
    React.createElement(
      'div',
      null,
      'world'
    ),
    'hello world'
  )
)

例如,如果新的虚拟DOM树与旧的虚拟DOM树有差异,React可能会生成一些DOM更新操作,如添加、移除或更新DOM元素,而这些操作都是应用在虚拟树上。通过虚拟树上的createElement来创建真实的元素。

应用DOM更新

React会将生成的DOM树更新操作应用到实际的DOM上,以反映最新的UI状态。

例如,如果需要添加新的DOM元素,React会将其添加到DOM树中;如果需要更新现有的DOM元素,则会更新对应的DOM属性和内容;如果需要移除DOM元素,则会将其从DOM树中移除。

React并不会每次调用render方法都直接操作实际的DOM。而是对虚拟树并进行比较和处理,然后再将最终的更新操作应用到实际的DOM上。这种通过虚拟DOM来管理和更新UI的方式,能够提高性能并减少不必要的DOM操作,从而改善用户体验。

总结

render将JSX编写的UI元素转换为虚拟dom树,最终会称为真实的节点,并且虚拟dom树可以通过diff算法来比较虚拟dom,高效的查找到需要更新的元素,通过操作虚拟树而非真实节点的方式来进行新增、更新、移除等操作。

如果觉得有趣或有收获,请关注我的更新,给个喜欢和分享。您的支持是我写作的最大动力!

往期好文推荐

相关推荐
海上彼尚2 小时前
Go之路 - 7.go的结构体
开发语言·后端·golang
源代码•宸7 小时前
分布式缓存-GO(分布式算法之一致性哈希、缓存对外服务化)
开发语言·经验分享·分布式·后端·算法·缓存·golang
It's now8 小时前
Spring AI 基础开发流程
java·人工智能·后端·spring
计算机毕设VX:Fegn08958 小时前
计算机毕业设计|基于springboot + vue图书商城系统(源码+数据库+文档)
java·数据库·vue.js·spring boot·后端·课程设计
哆啦A梦15888 小时前
商城后台管理系统 03 登录布局
javascript·vue.js·elementui
曼巴UE58 小时前
UE FString, FName ,FText 三者转换,再次学习,官方文档理解
服务器·前端·javascript
selt7919 小时前
Redisson之RedissonLock源码完全解析
android·java·javascript
夕颜1119 小时前
BeeAI 框架学习记录
后端
行走的陀螺仪9 小时前
高级前端 Input 公共组件设计方案(Vue3 + TypeScript)
前端·javascript·typescript·vue·组件设计方案
极市平台9 小时前
骁龙大赛-技术分享第5期(上)
人工智能·经验分享·笔记·后端·个人开发