多应用+插件架构,代码干净,二开方便,首家独创一键云编译技术,文档视频完善,免费商用码云13.8K 广告
前面已经写了一篇关于reactJS组件生命周期的博文,此篇博文是一个补充,增加了一些例子,有助于更好的理解reactJS组件。  **初始化阶段能够使用的钩子函数(按照触发顺序):**  **getDefaultProps**(获取实例的默认属性)————只有第一次实例的时候调用,实例之间共享引用(属性)  **getInitialState**(获取实例的初始状态)————初始化每个实例特有的状态  必须返回一个Object或者是Null  **componentWillMount**(组件即将被渲染到页面)——render之前最后一次修改状态的机会  **render**(组件在render中生成虚拟的DOM节点,即JSX,最后由React生成真实的DOM节点)——只能访问this.props和this.state,不应再访问其它信息,只有一个顶层组件,但是可以有子组件,不允许修改状态和DOM输出。  如果render需要修改状态和DOM输出,那么render就不能在服务端使用。并且,如果在render中修改状态和DOM输出,会使得代码逻辑变得复杂。所以,要尽可能避免这样做。  **componentDidMount**(组件被渲染到页面之后)——成功render并渲染完成真实DOM之后触发,可以修改DOM ~~~ <!DOCTYPE html> <html lang="en"> <head> <meta charset="UTF-8"> <meta name="Keywords" content="关键词一,关键词二"> <meta name="Description" content="网站描述内容"> <meta name="Author" content="刘艳"> <title></title> </head> <body> <div id = "example"></div> <div id = "example2"></div> </body> </html> <script src="build/jquery-1.11.2.min.js"></script> <script src="build/react.js"></script> <script src="build/react-dom.js"></script> <script src="build/browser.min.js"></script> <script type="text/babel"> var MyComponent = React.createClass({ getDefaultProps: function(){ console.log("获取实例的默认属性"); return{name: "Yvette"}; }, getInitialState: function () { console.log("获取实例的初始状态"); return{will:true}; }, componentWillMount: function () { console.log("组件即将被渲染到页面"); }, handleClick: function(event){ this.setState({will: !this.state.will}); }, componentDidMount: function(){ console.log("aaaa"); if(this.state.will){ $(this.refs.example).append("啦啦啦"); }else{ $(this.refs.example).append("郁闷"); } }, render: function(){ console.log("render"); return( <div> <p ref = "example" onClick = {this.handleClick}>{this.props.name}未来{this.state.will ? "会" : "不会"}更好!</p> </div> ) } }); ReactDOM.render(<MyComponent/>,document.querySelector("#example")); ReactDOM.render(<MyComponent/>,document.querySelector("#example2")); </script> ~~~ ![](https://box.kancloud.cn/2016-04-07_5706040076301.jpg)  从运行结果可以看出:  1、获取默认属性(getDefaultProps)只会在第一次实例化组件时运行一次,后面不会再运行,  2、获取初始状态(getInitialState)和componentWillMount,render,componentDidMount在每次实例化组件时,都会进入.  3、点击切换时,只会触发render函数,因此我们写在componentDidMount函数中的状态判断不会再被执行. **运行中阶段能够使用的钩子函数(按照触发顺序):**  **componentWillReceiveProps**(组件快要接收到属性时触发)——父组件修改属性触发,可以修改新属性、修改状态。  在修改发生之前出发。在属性真正比传送到组件之前,对其进行处理。  **shouldComponentUpdate**(组件接收到新状态时,是否需要更新,返回false,React就不会更新,可以提高性能)  **componentWillUpdate**(组件即将更新到页面)——不能修改属性和状态,会导致死循环  **render**——只能访问this.props和this.state,不应再访问其它信息,只有一个顶层组件,但是可以有子组件,不允许修改状态和DOM输出。  **componentDidUpdate**(在组件更新到页面之后调用)——可以修改DOM ~~~ <body> <div id = "example"></div> <div id = "example2"></div> </body> </html> <script src="build/jquery-1.11.2.min.js"></script> <script src="build/react.js"></script> <script src="build/react-dom.js"></script> <script src="build/browser.min.js"></script> <script type="text/babel"> var MyComponent = React.createClass({ getDefaultProps: function(){ console.log("获取实例的默认属性"); return{name: "Yvette"}; }, getInitialState: function () { console.log("获取实例的初始状态"); return{will:true}; }, componentWillMount: function () { console.log("组件即将被渲染到页面"); }, handleClick: function(event){ this.setState({will: !this.state.will}); }, componentDidMount: function(){ console.log("组件被渲染到页面之后"); $(this.refs.example).append("啦啦啦"); }, render: function(){ console.log("render") return( <div> <p ref = "example" onClick = {this.handleClick}>{this.props.name}未来{this.state.will ? "会" : "不会"}更好!</p> </div> ); }, componentWillReceiveProps: function(){ console.log("组件快要接收到属性"); }, shouldComponentUpdate: function(){ console.log("是否需要更新"); return false; }, componentWillUpdate: function(){ console.log("组件即将被更新"); }, componentDidUpdate: function(){ console.log("组件更新被渲染到页面"); } }); ReactDOM.render(<MyComponent/>,document.querySelector("#example")); ReactDOM.render(<MyComponent/>,document.querySelector("#example2")); </script> ~~~ 运行结果如下:  ![](https://box.kancloud.cn/2016-04-07_570604008875d.jpg)  从运行结果可以看出:  **1、在运行过程中,组件的状态发生改变时,首先进入shouldComponentUpdate函数,即组件是否需要更新,如果返回false,表示无需更新,直接返回。** ~~~ <body> <div id = "example"></div> <div id = "example2"></div> </body> </html> <script src="build/jquery-1.11.2.min.js"></script> <script src="build/react.js"></script> <script src="build/react-dom.js"></script> <script src="build/browser.min.js"></script> <script type="text/babel"> var MyComponent = React.createClass({ getDefaultProps: function(){ console.log("获取实例的默认属性"); return{name: "Yvette"}; }, getInitialState: function () { console.log("获取实例的初始状态"); return{will:true}; }, componentWillMount: function () { console.log("组件即将被渲染到页面"); }, handleClick: function(event){ this.setState({will: !this.state.will}); }, componentDidMount: function(){ console.log("组件被渲染到页面之后"); //$(this.refs.example).append("啦啦啦"); }, render: function(){ console.log("render") return( <div> <p ref = "example" onClick = {this.handleClick}>{this.props.name}未来{this.state.will ? "会" : "不会"}更好!</p> <span ref = "more">啦啦啦</span> </div> ); }, componentWillReceiveProps: function(){ console.log("组件快要接收到属性"); }, shouldComponentUpdate: function(){ console.log("是否需要更新"); return true; }, componentWillUpdate: function(){ console.log("组件即将被更新"); $(this.refs.example).css({"background": "#ccc","line-height":"30px"}); //this.setState({will: !this.state.will});//导致一个死循环 }, componentDidUpdate: function(){ console.log("组件更新被渲染到页面"); if(this.state.will){ $(this.refs.more).html("啦啦啦"); } else{ $(this.refs.more).html("郁闷"); } } }); ReactDOM.render(<MyComponent/>,document.querySelector("#example")); ReactDOM.render(<MyComponent/>,document.querySelector("#example2")); </script> ~~~ ![](https://box.kancloud.cn/2016-04-07_570604009b2f7.jpg)  从运行结果可以看出钩子函数的触发顺序: 1、shouldComponentUpdate,必须返回true或false,如果返回false,直接返回,不会再触发后面的钩子函数。 2、componentWillUpdate和componentDidUpdate中都可以操作DOM元素,因为当前在运行过程中,组件已经被渲染到了页面。但是最后是在componentDidUpdate中进行修改。 **销毁中阶段能够使用的钩子函数(按照触发顺序):**  **componentWillUnmount**(在销毁操作执行之前触发)——在组件真正被销毁前调用,在删除组件之前进行清理操作,如计时器和事件监听器。 ~~~ <body> <div id = "example"></div> </body> </html> <script src="build/react.js"></script> <script src="build/react-dom.js"></script> <script src="build/browser.min.js"></script> <script type="text/babel"> var style = { color: "red", border: "1px solid #000" }; var HelloWorld = React.createClass({ render: function(){ return <p>Hello, {this.props.name ? this.props.name : "World"}</p>; }, componentWillUnmount: function(){ console.log("I will unmount"); } }); var HelloUniverse = React.createClass({ getInitialState: function(){ return {name: "Yvette"}; }, handleChange: function (event) { if(event.target.value == "123"){ React.unmountComponentAtNode(document.querySelector("#example")) return; } this.setState({name: event.target.value}); }, render: function(){ return( <div> <HelloWorld name = {this.state.name}></HelloWorld> <br/> <input type = "text" onChange = {this.handleChange} /> </div> ); } }); ReactDOM.render(<div style = {style}><HelloUniverse></HelloUniverse></div>,document.querySelector("#example")); </script> ~~~ 当输入结果为123时,触发componentWillUnmount钩子函数。