旧版本中的 render
方法只作了一件事,就是调起 diff
方法,新版本中的 render
引入了 Fragment
,让咱们写的自定义组件都成了子组件。node
React.Fragment
Fragment
就是让 react
组件可以聚合一个个子元素列表,那样就没必要要在增长一个额外的节点了react
// 旧的写法
render(){
return (
<div> <ChildA /> <ChildB /> <ChildC /> </div>
)
}
// Fragment
render(){
return (
<> <ChildA /> <ChildB /> <ChildC /> </> ) } 复制代码
<></>
实际上是 <React.Fragment/>
的语法糖,当组件中须要遍历数组传递 key
值时,就须要使用 <React.Fragment/>
git
render(){
return (
<div> { goodsList.map(item => ( <React.Fragment key={item.id}> <p>{item.goodsName}</p> </React.Fragment> )) } </div> ) } 复制代码
了解了 react
的 Fragment
,那 preact
是如何使用和实现的呢:github
使用:api
import {h, render, Component, Fragment} from 'preact';
class App extends Component {
render(){
return (
<Fragment> <div>preact</div> <div>使用了Fragment</div> </Fragment>
)
}
}
复制代码
在 preact
中,并无相似 <></>
这样的语法糖,下面来看下它的实现原理:数组
function Fragment() {}
function render(vnode, parentDom, replaceNode) {
// ...
vnode = createElement(Fragment, null, [vnode]);
// ...
}
复制代码
在 render
方法中调用了 createElement
方法建立了一个虚拟 dom
,第一个参数就是 Fragment
,实参是一个 function
。createElement
这个函数的第一个形参 type
是这个虚拟 dom
的类型,它有多是 div,span
等,也有多是一个 function
,当讲到 diff
时,会专门有一个分支就是判断 type === Fragment
的状况,那个时候再细讲,这里只简单说下结果:dom
Fragment
做为虚拟dom的类型传入,在diff
一个组件时,时若是遇到type === Fragment
时,就直接diff
<Fragment></Fragment>
包裹的子节点,而这些子节点所渲染的真实dom
会直接挂载在<Fragment></Fragment>
所对应的父节点上。函数
以上就是 Fragment
的简单实现,在 render
方法中,经过 createElement
方法从新建立的 vnode
会传入 diffChildren
方法中,这个方法是整个新版中最核心的方法,将在后面专门会说这个方法,这里能够简单的理解为--对比这个 vnode
下的子节点是否更新。spa
在这个 render
方法中,因为最外层包裹的是一个 Fragment
,因此,这里的 diffChildren
比对的对象就是 Fragment
包裹下的子节点。code
下一章,咱们就来看看这个 diffChildren
方法。