这一章可能比较长,因为这一章我会把生命周期,transaction,setState放到一起说明. 组件的生命周期分为二个部分
- 组件的挂载
- 组件的更新
组件的挂载
在上一章对于组件的挂载已经做了详细的说明,但是涉及到组件生命周期部分被略过.接下来我将对其深入解析. 组件的挂载涉及到二个比较重要的生命周期方法componentWillMount和componentDidMount.
componentWillMount
对于componentWillMount这个函数玩过React的都知道他是组件render之前的触发. 但是如果我再具体点呢. 是在实例之前?还是实例之后?还是构建成真实dom之前?还是构建成真实dom之前,渲染之前?估计很多人不知道吧.所以在面试的时候无论你对React有多熟,还是尽量不要说"精通"二字.(大佬除外)
componentWillMount是组件更新之前触发,所以直接从ReactCompositeComponent.mountComponent里面找
// this.performInitialMount
if (inst.componentWillMount) {
debugger
if ("development" !== "production") {
measureLifeCyclePerf(
function() {
return inst.componentWillMount();
},
debugID,
"componentWillMount"
);
} else {
inst.componentWillMount();
}
// When mounting, calls to `setState` by `componentWillMount` will set
// `this._pendingStateQueue` without triggering a re-render.
if (this._pendingStateQueue) {
inst.state = this._processPendingState(
inst.props,
inst.context
);
}
}
复制代码
代码在performInitialMount函数里面,所以在实例之后,虚拟dom构建真实dom之前触发的
componentDidMount
直接看代码吧
var markup;
if (inst.unstable_handleError) {
markup = this.performInitialMountWithErrorHandling(
renderedElement,
hostParent,
hostContainerInfo,
transaction,
context
);
} else {
markup = this.performInitialMount(
renderedElement,
hostParent,
hostContainerInfo,
transaction,
context
);
}
if (inst.componentDidMount) {
if ("development" !== "production") {
transaction
.getReactMountReady()
.enqueue(function() {
measureLifeCyclePerf(
function() {
return inst.componentDidMount();
},
_this._debugID,
"componentDidMount"
);
});
} else {
transaction
.getReactMountReady()
.enqueue(
inst.componentDidMount,
inst
);
}
}
复制代码
它是出现在markup(真实dom)之后.但是肯定不会在这里面执行,因为在markup还没插入到container里面呢。回顾一下上一章的内容MountComponentIntoNode方法mountComponent之后还有个setInnerHTML(container, markup)只有这个函数执行完之后componentDidMount才能执行.
注意performInitialMount方法 看看下面的代码
class A extends React.Component {
render(){
return <K />
}
}
<App>
<A />
</App>
复制代码
this.componentDidMount的执行顺序是K-->A--->App<(ljs-title">function() {
measureLifeCyclePerf(
inst.componentDidUpdate.bind(
inst,
prevProps,
prevState,
prevContext
),
_this2._debugID,
"componentDidUpdate"
);
});
} else {
transaction
.getReactMountReady()
.enqueue(
inst.componentDidUpdate.bind(
inst,
prevProps,
prevState,
prevContext
),
inst
);
}
}
复制代码
是不是感到非常眼熟,跟组件的挂载非常类似, 先执行componentWillUpdate方法然后通过_updateRenderedComponent递归的更新组件,更新完成之后执行transaction里面的Wrapper中的close方法, close将释放componentDidUpdate的队列.
说到这里,组件的生命周期也就是讲完了. 还有三个比较核心的点.
diff算法 (同级之间的比较,更新前后的虚拟dom到底是如何对比的)- 事件系统, (
React合成系统到底是什么?) fiber架构 (React16版本革命性的变革)




