当前位置: 首页 > news >正文

做养生网站怎么样小程序制作永久免费

做养生网站怎么样,小程序制作永久免费,南宁网站建设q479185700棒,洛南网站建设函数式组件只有属性,没有状态,更没有生命周期的概念,但是函数式组件在React16.8引入hooks以后,可以在函数式组件里使用state和生命周期等特性,拥有类似于类组件的能力,同时保持简洁和易用性。 在生命周期的…

函数式组件只有属性,没有状态,更没有生命周期的概念,但是函数式组件在React16.8引入hooks以后,可以在函数式组件里使用state和生命周期等特性,拥有类似于类组件的能力,同时保持简洁和易用性。

在生命周期的某个阶段会触发的东西

写不写本身不会影响组件的执行,但是写的话会在生命周期的某个阶段触发

整个生命中周期分为三个阶段:初始化阶段、运行阶段、销毁阶段

初始化阶段

执行顺序:WillMount=>render=>DidMount
import React, { Component } from 'react';class App extends Component {state={myname:'荷叶饭'}componentWillMount() {console.log('WillMount', this.state.myname, document.getElementById('myname'))//WillUnmount,将要挂载到组件中,只会执行一次,上树(上dom树)前的最后一次修改状态的机会,但是拿不到dom//简单说就说初始化数据的作用this.setState({myname:'励志轩'})
}componentDidMount() {console.log('DidMount',document.getElementById('myname'))//DidMount,已经挂载到组件中,只会执行一次//一般放置数据请求,axios,ajax,订阅函数的调用,setInterval//基于创建完的dom进行初始化,BetterScroll就说基于创建完的dom来让长列表滚动}render() {console.log('render')// 写完以后会自动执行return (//render里不能直接修改状态,所以WillMount是上树前的最后一次修改状态的机会<div><span id='myname'>{ this.state.myname}</span></div>);}
}export default App;
React中的生命周期函数,也叫做钩子函数,钩子函数起到的作用是被咬钩的时候我知道了
这里报警告是因为WillMount 生命周期方法,该方法在 React 16.3 之后已被标记为 不安全的(unsafe),所以上面写的东西只适用于React16.2以前
我真是服了缝缝补补的前端

React版本的重要节点:16.2之前都是老版本的生命周期函数,使用的时候可以自己将其重命名为UNSAFE_componentWillMount,相当于自己提醒自己

警告消失了:

因为在16.2以后优化了diff(新的对比旧的)算法,提出了Fiber(纤维,新协调算法,支持异步渲染、渲染优先级调度),WillMount就属于进行diff算法的部分,为第一优先级,以前来说要等它执行完毕,但是根据新的机制会打断第一优先级,所以在后期的使用就有了安全隐患
函数组件在 16.8之前也是没有生命周期的
用我们刚学的componentDidMount来做数据请求
WillMount应用实例
import React, { Component } from 'react';
import BetterScroll from 'better-scroll'
class App extends Component {state = {list:['111','222','333','444','555','666','777','888','999','121']}UNSAFE_componentWillMount() {//获取不了dom节点}componentDidMount() {//可以获取dom节点new BetterScroll('#wrapper')}render() {return (<div><div id='wrapper' style={{background:'yellow',height:'200px',overflow:'hidden'}}><ul>{this.state.list.map(item => <li key={item}>{item}</li>)}</ul></div></div>);}
}export default App;

运行中阶段

看看他们render、componentDidUpdate、componentWillUpdate三个的执行顺序:
import React, { Component } from 'react';class App extends Component {state = {myname:'kerwin'
}render() {console.log('render')return (<div><button onClick={() => {this.setState({myname:'tiechui'})}}>click</button><span id='myname'> {this.state.myname}</span></div>)}UNSAFE_componentWillUpdate() {console.log('componentWillUpdate',document.getElementById('myname').innerHTML)}componentDidUpdate() {console.log('componentDidUpdate',document.getElementById('myname').innerHTML)}}export default App;
render=>点击按钮=>componentWillUpdate=>render=>componentDidUpdate
先渲染=>点击按钮以后=>准备更新=>正在更新=>更新完成
每次更新完dom的时候new一个BetterScroll,加上if判断可以防止new多次的BetterScroll
import React, { Component } from 'react';
import BetterScroll from 'better-scroll'import axios from 'axios'
class App extends Component {state = {myname: 'kerwin',list:[]
}componentDidMount() {axios.get('/test.json').then(res => {console.log(res.data.data.films)this.setState({list:res.data.data.films},)})
}render() {console.log('render')return (<div><button onClick={() => {this.setState({myname:'tiechui'})}}>click</button><span id='myname'> {this.state.myname}</span><div id='wrapper' style={{height:'100px',overflow:'hidden',background:'pink'}}><ul>{this.state.list.map(item => <li key={item.filmId}>{item.name}</li>)}</ul></div></div>)}UNSAFE_componentWillUpdate() {console.log('componentWillUpdate',document.getElementById('myname').innerHTML)}componentDidUpdate(prevProps,prevState) {console.log('componentDidUpdate', document.getElementById('myname').innerHTML)if (prevState.list.length === 0) {new BetterScroll('#wrapper')}}}export default App;

但是如果只有这个三个普通的生命周期函数,那么只要点击按钮,即使state并没有变化,也会调用render函数

SCU

这时候就需要shouldComponentUpdate,这个函数简称SCU,性能优化函数(同理CDM是componentDidMount,),来判断组件是否应该更新:

shouldComponentUpdate(nextProps,nextState) {//return true//应该更新//return false//阻止更新//做条件判断:if (this.state.myname!==nextState.myname) {return true}return false
}

如果要对比的内容是对象,可以转化为json字符串对比:

SCU优化性能的案例:
import React, { Component } from 'react';class Box extends Component{
//优化思路:只拿改变的div和前一个做对比就好了shouldComponentUpdate(nextProps) {if (this.props.current===this.props.index||nextProps.current===nextProps.index) {return true}return false
}render() {return <divstyle={{ width: '100px', height: '100px', border: this.props.current === this.props.index ? '5px solid red' : '5px solid grey', margin: '10px', float: 'left' }}></div>}
}class App extends Component {state = {list: ['00', '01', '02', '03', '04', '05', '06', '07', '08', '09', '10',],current:0
}render() {return (<div><input type='number' onChange={(e) => {console.log(e.target.value)this.setState({current:Number(e.target.value)})}} /><div style={{overflow:'hidden'}  }>{this.state.list.map((item, index) => <Box key={item} current={this.state.current} index={index} />)}</div></div>);}
}export default App;

最先获取父组件传来的属性,相当于子组件里的初始化

import React, { Component } from 'react';class Child extends Component{state = {title:''}render() {return (<div>child-{this.state.title}</div>)}UNSAFE_componentWillReceiveProps(nextProps) {console.log(' UNSAFE_componentWillReceiveProps',this.props.text)//第一次点击按钮拿到的是老属性,11111111console.log(' UNSAFE_componentWillReceiveProps', nextProps)//拿到的是新属性,22222222//该生命周期最先获得父组件传来的属性,可以利用属性进行ajax或者逻辑处理//把拿到的属性转化为自己孩子的状态this.setState({title:nextProps.text+'荷叶饭'})}
}class App extends Component {state = {text:'11111111'
}render() {return (<div>{this.state.text}<button onClick={() => {this.setState({text:'22222222'})}}>click</button><Child text={this.state.text} /></div>);}
}export default App;

请求到的是老的数据,需要加入形参nextProps

componentWillReceiveProps

外部组件多次频繁更新传入多次不同的 props ,会导致不必要的异步请求
/** @作者: kerwin* @公众号: 大前端私房菜*/
import React, { Component } from 'react'
import axios from 'axios'
export default class App extends Component {state = {type:1}render() {return (<div><ul><li onClick={()=>{this.setState({type:1})}}>正在热映</li><li onClick={()=>{this.setState({type:2})}}>即将上映</li></ul><FilmList type={this.state.type}></FilmList></div>)}
}class FilmList extends Component{state = {list:[]}//初始化-执行一次componentDidMount() {// console.log(this.props.type)if(this.props.type===1){//请求卖座正在热映的数据console.log("请求卖座正在热映的数据")axios({url:"https://m.maizuo.com/gateway?cityId=110100&pageNum=1&pageSize=10&type=1&k=6369301",headers:{'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.2.0","e":"16395416565231270166529","bc":"110100"}','X-Host': 'mall.film-ticket.film.list'}}).then(res=>{console.log(res.data.data.films)this.setState({list:res.data.data.films})})}else{//请求卖座即将上映的数据console.log("请求卖座即将上映的数据")axios({url:"https://m.maizuo.com/gateway?cityId=110100&pageNum=1&pageSize=10&type=2&k=8077848",headers:{'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.2.0","e":"16395416565231270166529","bc":"110100"}','X-Host': 'mall.film-ticket.film.list'}}).then(res=>{console.log(res.data.data.films)this.setState({list:res.data.data.films})})}}UNSAFE_componentWillReceiveProps(nextProps){if(nextProps.type===1){//请求卖座正在热映的数据console.log("请求卖座正在热映的数据")axios({url:"https://m.maizuo.com/gateway?cityId=110100&pageNum=1&pageSize=10&type=1&k=6369301",headers:{'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.2.0","e":"16395416565231270166529","bc":"110100"}','X-Host': 'mall.film-ticket.film.list'}}).then(res=>{console.log(res.data.data.films)this.setState({list:res.data.data.films})})}else{//请求卖座即将上映的数据console.log("请求卖座即将上映的数据")axios({url:"https://m.maizuo.com/gateway?cityId=110100&pageNum=1&pageSize=10&type=2&k=8077848",headers:{'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.2.0","e":"16395416565231270166529","bc":"110100"}','X-Host': 'mall.film-ticket.film.list'}}).then(res=>{console.log(res.data.data.films)this.setState({list:res.data.data.films})})}}render(){return <ul>{this.state.list.map(item=><li key={item.filmId}>{item.name}</li>    )}</ul>}
}

销毁阶段

例如你在组件里写了一个定时器,即使组件删除了定时器也还在,就会降低性能,这时候就需要在销毁阶段销毁定时器

进行清理操作的生命周期函数

import { isCancel } from 'axios';
import React, { Component } from 'react';class App extends Component {state = {isCreated:false
}render() {return (<div><button onClick={() => {this.setState({isCreated:!this.state.isCreated})}}>click</button>{/* {this.state.isCreated?<Child></Child>:''} */}{this.state.isCreated&&<Child></Child>}</div>);}
}class Child extends Component {render() {return (<div>child</div>)}componentDidMount() {window.onresize = () => {console.log('resize')}//绑在window上的定时器,如果只卸载组件定时器还会运行this.timer=setInterval(() => {console.log('我是定时器')}, 1000);}componentWillUnmount() {console.log('componentWillUnmount') //销毁child组件的同时销毁事件监听和定时器clearInterval(this.timer)window.onresize=null}
}export default App;

新的生命周期的替代

修复旧生命周期函数的警告

getDerivedStateFromProps

初始化的时候代替componentWillMount,在ssr中 这个方法将会被多次调用, 所以会重复触发多遍,同时在这里如果绑定事件, 将无法解绑,导致内存泄漏 , 变得不够安全高效逐步废弃。

在后续更新的时候取代componentWillReceiveProps 外部组件多次频繁更新传入多次不同的 props,会导致不必要的异步请求

该函数涵盖了初始化和更新阶段,适用于这两个阶段都重复执行的逻辑

第一次的初始化组件以及后续的更新过程中(包括自身状态更新以及父传子)

返回一个对象作为新的state,返回null则说明不需要在这里更新state

需要静态方法,返回一个对象

把传过来的state.myname转为首字母大写

import React, { Component } from 'react';class App extends Component {state = {myname: 'kerwin',myage:19}//componentWillMount 初始化static getDerivedStateFromProps(nextProps,nextState) {console.log('getDrivedStateFromProps',nextState)//在这个生命周期内做最后的修改,return的结果会把原来的state对象和返回的对象合并return {//实现首字母大写效果myname:nextState.myname.substring(0,1).toUpperCase()+nextState.myname.substring(1)}
}render() {return (<div><button onClick={() => {this.setState({myname:'heyefan'})}}>click</button>{/* 同名的覆盖掉,不同名的保留 */}app-{this.state.myname}-{this.state.myage}</div>);}
}export default App;

修改之前的案例:

import React, { Component } from 'react'
import axios from 'axios'
export default class App extends Component {state = {type:1}render() {return (<div><ul><li onClick={()=>{this.setState({type:1})}}>正在热映</li><li onClick={()=>{this.setState({type:2})}}>即将上映</li></ul><FilmList type={this.state.type}></FilmList></div>)}
}class FilmList extends Component{state = {list:[]}//初始化-执行一次componentDidMount() {// console.log(this.props.type)if(this.props.type===1){//请求卖座正在热映的数据console.log("请求卖座正在热映的数据")axios({url:"https://m.maizuo.com/gateway?cityId=110100&pageNum=1&pageSize=10&type=1&k=6369301",headers:{'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.2.0","e":"16395416565231270166529","bc":"110100"}','X-Host': 'mall.film-ticket.film.list'}}).then(res=>{console.log(res.data.data.films)this.setState({list:res.data.data.films})})}else{//请求卖座即将上映的数据console.log("请求卖座即将上映的数据")axios({url:"https://m.maizuo.com/gateway?cityId=110100&pageNum=1&pageSize=10&type=2&k=8077848",headers:{'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.2.0","e":"16395416565231270166529","bc":"110100"}','X-Host': 'mall.film-ticket.film.list'}}).then(res=>{console.log(res.data.data.films)this.setState({list:res.data.data.films})})}}static getDerivedStateFromProps(nextProps,nextState) {console.log('getDrivedStateFromProps',nextProps)//根据props和state的变化计算新的state,return的结果会把原来的state对象和返回的对象合并//此处不能执行异步请求,因为执行完会立马return,这样异步的结果就永远不会返回,也无法进行setState更新return {type:nextProps.type}}//通过this.setState把获取的数据转化为状态,配合componentDidUpdatecomponentDidUpdate(prevState) {//getDerivedStateFromProps做多次父子请求最后合并为一次,最后在此处处理console.log(this.state.type)if (this.state.type === prevState.type) {return}if(this.state.type===1){//请求卖座正在热映的数据console.log("请求卖座正在热映的数据")axios({url:"https://m.maizuo.com/gateway?cityId=110100&pageNum=1&pageSize=10&type=1&k=6369301",headers:{'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.2.0","e":"16395416565231270166529","bc":"110100"}','X-Host': 'mall.film-ticket.film.list'}}).then(res=>{console.log(res.data.data.films)this.setState({list:res.data.data.films})})}else{//请求卖座即将上映的数据console.log("请求卖座即将上映的数据")axios({url:"https://m.maizuo.com/gateway?cityId=110100&pageNum=1&pageSize=10&type=2&k=8077848",headers:{'X-Client-Info': '{"a":"3000","ch":"1002","v":"5.2.0","e":"16395416565231270166529","bc":"110100"}','X-Host': 'mall.film-ticket.film.list'}}).then(res=>{console.log(res.data.data.films)this.setState({list:res.data.data.films})})}}render(){return <ul>{this.state.list.map(item=><li key={item.filmId}>{item.name}</li>    )}</ul>}
}

getSnapshotBeforeUpdate

实现定位重点功能:

willupdate记录高度

didupdate访问容器高度

scrollTop=此时容器高度-willupdate记录的高度

但是willupdate有副作用,在render的过程中容易被打断,在didupdate访问前有各种不可控事件可能发生,导致记录的高度不准

所以用getSnapshotBeforeUpdate(执行dom前的一刻拍了个shot)取代willupdate,来记录高度,所以必须有返回值

来邮件之后自动滚到之前对应邮件的高度
import React, { Component } from 'react';class App extends Component {state = {list: [1, 2, 3, 4, 5, 6, 7, 8, 9]}myref=React.createRef()getSnapshotBeforeUpdate() {//获取容器高度console.log(this.myref.current.scrollHeight)return this.myref.current.scrollHeight}componentDidUpdate(prevProps,prevState,value) {console.log(this.myref.current.scrollHeight)this.myref.current.scrollTop+=this.myref.current.scrollHeight-value}render() {return (<div><button onClick={() => {this.setState({list:[...[11,12,13,14,15,16],...this.state.list]})}}>来邮件</button><h1>邮箱应用</h1><div style={{height:'200px',overflow:'auto'}} ref={this.myref}><ul>{this.state.list.map(item => <li key={item} style={{ height: '100px', background: 'pink' }}>{item}</li>)}</ul></div></div>)}}export default App;

可以看到添加了几个邮件可以自动跳转到对应的高度

添加css文件以后可以更丝滑

react中性能优化的方案

1. shouldComponentUpdate

控制组件自身或者子组件是否需要更新,尤其在子组件非常多的情况下, 需要进行优化。

2. PureComponent

在引入的时候替换:

import React, { PureComponent } from 'react';class ComponentName extends PureComponent {render() {return (<div>Content</div>);}
}export default ComponentName;

PureComponent会帮你 比较新props 跟 旧的props, 新的state和老的state(值相等,或者

对象含有相同的属性、且属性值相等 ),决定shouldcomponentUpdate 返回true 或者

false, 从而决定要不要呼叫 render function

注意:

如果你的 state props 『永远都会变』,那 PureComponent 并不会比较快,因为

shallowEqual 也需要花时间。

http://www.dtcms.com/a/509561.html

相关文章:

  • 怎么查自己专业是否符合一建系统优化是什么意思
  • 网站建设推广语言鄂尔多斯建设局网站
  • 手机网站制作步骤我为什么不建议年轻人做运营
  • 宜春招聘网站开发区招工徐州市城乡建设局官方网站
  • 通配符对称冲突检测工具
  • Linux小课堂: 数据处理核心命令之grep、sort、wc、uniq 与 cut 的深度解析
  • 深圳建筑设计平台网站wordpress wp posts
  • 北京住房和城乡建设官方网站色彩搭配比较好的网站
  • 找到网站后台地址如何做自己网站
  • 有没有人做网站大学做html个人网站素材
  • 嘉兴五县两区网站建设局机关网站建设
  • 江苏省交通建设厅门户网站wordpress如何修改首页文件模板
  • 如何建立一个网站详细步骤通辽住房和城乡建设厅网站
  • 网站设计需要多少钱小程序开发教程 下载
  • 公司无网站无平台怎么做外贸2021最火关键词
  • 手机网站的静态页面官网站站
  • 蒙古网站后缀国内知名设计工作室
  • 单页网站怎么制作昆明企业网站建设公司
  • 建设银行兰州分行网站百度小程序开发平台
  • 朝阳网站建设 慈云寺厦门易尔通网站建设好吗
  • 网站 备案 哪个省建设培训中心网站
  • 成都大型网站建设公司iis网站属性在哪
  • 中国站长查询域名备案西安有哪些做网站的公司好
  • 东莞定制网站建设jsp网站部署怎么做
  • 百度推广太原网站建设阿里云服务器添加网站
  • 2016网站优化今天深圳新增确诊最新消息
  • 驾校官方网站 模板wordpress手动装插件
  • 怎样直接输入网址打开网站ps做网站标签
  • 甘肃肃第八建设集团网站1wordpress关联adsense
  • 长沙做网站开发多少钱服务行业做网站