React 15
React 15 是 React 库的一个重要版本,于 2016 年 4 月发布。它在性能、架构和功能方面进行了相关改进。
架构
React 15 的架构基于早期的 Reconciler,采用不可中断的递归同步渲染策略(Legacy Stack Reconciler),一次性完成虚拟 DOM 的比较和真实 DOM 的更新。
由于同步渲染,在复杂应用中,可能阻塞主线程,导致页面卡顿。Stack Reconciler Example
简易实现
- App.js
- react-dom.js
- react.js
- shard.js
import React from './react.js'
import ReactDOM from './react-dom.js'
/*
通过 babel 或 swc 进行编译,转换成
React.createElement('div',{ class: 'box'}, chidlren)
*/
const element = (
<div className='box'>
<p>text 1</p>
<span>text 2</span>
</div>
)
ReactDOM.render(element, document.getElement('root'))
import { isProperty, isEvent } from './shared'
function render(element, contianer) {
const dom = createDOM(element.type)
Object.keys(element.props)
.filter(isProperty)
.forEach((prop) => {
const propValue = element.props[prop]
if (isEvent(prop, propValue)) {
dom.addEventListener(getEventName(prop), propValue)
} else {
dom[prop] = propValue
}
})
// 不可中断的递归渲染,阻塞主线程
element.props.children.forEach((child) => {
render(child, dom)
})
contianer.appendChild(dom)
}
export default {
render
}
import { isObject } from './shared.js'
function createElement(type, props, ...children) {
return {
type,
props: {
...props,
children: children.map((child) => {
if (isObject(child)) {
return child
}
return createTextElement(child)
})
}
}
}
export default {
createElement
}
function createTextElement(text) {
return {
type: 'text',
props: {
nodeValue: text,
children: []
}
}
}
export function isObject(value) {
return typeof value === 'object' && value !== null
}
export function isProperty(property) {
return property !== 'children' && !isEvent(property)
}
export function isEvent(property, value) {
return property.startsWith('on') && typeof value === 'function'
}
export function getEventName(prop) {
return prop.replace('on', '').toLowerCase()
}
主要更新
- 改进的虚拟 DOM 和性能优化。改进了 DOM 更新和渲染的 diff 算法,提升了高频次更新的性能。
- 更好的 DOM 属性处理。对 DOM 属性的处理进行了全面更新,变得更加接近规范。
- 增强 SVG 支持。允许直接使用 SVG 标签和属性而无需额外配置。
- 更小的渲染包。React 15 对渲染器代码进行优化,使打包后的体积更小,从而减小了加载时间。
- React 和 ReactDOM 分离。React 15 进一步强化了 react 和 react-dom 的分离,React 专注于组件逻辑,而 ReactDOM 负责浏览器环境的渲染。
- 错误边界改进。引入了捕获渲染错误的基础能力,为后续版本作准备。
- 警告机制增强。加强了开发模式下的警告机制,帮助开发者更早发现问题,如唯一键、属性类型验证等。