React类组件

React类组件是通过ES6类的方式来创建组件,React会解释组件标签找到组件,发现这个组件是通过类定义的,就会在内部通过new的操作来创建出类的实例,并通过这个实例调用原型上的render方法,将render返回的虚拟DOM转换成真实DOM呈现在页面中。

组件三大核心属性之state

state是组件对象最重要的属性,值是一个对象,可以包含多个key-value的组合,更新state可以更新对应的页面显示,即重新渲染组件

1
2
3
4
5
6
7
8
9
10
11
12
13
class App extends React.Component{
state = {name:'hailee',age:25}
changeName = ()=>{ //这里必须写箭头函数
this.setState({name:'Haley'}) //setState有两种写法
}
reder(){
const {name,age} = this.state
return <div>
<h1>我叫{name},我今年{age}岁了</h1>
<button onClick={this.changeName} />
</div>
}
}

Question 1:为什么类中的方法要写成箭头函数的形式?答案代码解释如下,因为p1.speak不是通过实例调用的,而是通过赋值给另外一个变量,另一个变量进行调用,这个时候调用的this应该是全局的window,但是因为类中默认开启了严格模式,所以是undefined

1
2
3
4
5
6
7
8
9
10
11
12
13
class Person {
constructor(name,age){
this.name = name
this.age = age
}
speak(){
console.log(this)
}
}
const p1 = new Person('hailee',25)
p1.speak() //this为Person实例对象
const x = p1.speak
x() //this为undefined,因为类中的方法默认开启了严格模式,所以不是window

组件三大核心属性之props

每个组件对象都有props属性,组件标签的所有属性都保存在props中

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
class Parent extends React.Component{
state = {name:'hailee',age:25}
changeName = ()=>{ //这里必须写箭头函数
this.setState({name:'Haley'}) //setState有两种写法
}
reder(){
const {name,age} = this.state
return <div>
<h1>我叫{name},我今年{age}岁了</h1>
<Child name={name}/>
<button onClick={this.changeName} />
</div>
}
}
Class Child extends React.Component{
return <div>
我是来自于父组件的{this.props.name}
</div>
}

组件三大核心属性之ref

无论是组件还是标签都可以通过ref属性标识自己

  1. 字符串形式的ref,
1
2
3
4
5
6
7
8
9
10
11
class App extends React.Component{
showData = ()=>{
console.log(this.refs.input1.value)
}
reder(){
return <div>
<input ref="input1"/>
<button onClick={this.showData}/>
</div>
}
}
  1. 回调函数形式的ref
1
2
3
4
5
6
7
8
9
10
11
12
class App extends React.Component{
showData = ()=>{
const {inputRef} = this
console.log(inputRef.value)
}
reder(){
return <div>
<input ref={c => this.inputRef = c}/>
<button onClick={this.showData}/>
</div>
}
}
  1. React.createRef()调用后会返回一个容器,这个容器储存了ref所标识的节点,React V16.3引入
1
2
3
4
5
6
7
8
9
10
11
12
class App extends React.Component{
myRef = React.createRef()
showData = ()=>{
console.log(this.myRef.current.value)
}
reder(){
return <div>
<input ref={this.myef}/>
<button onClick={this.showData}/>
</div>
}
}

React函数组件

react函数组件是通过javascript函数构建的组件,函数组件可以接受props作为参数。与类组件相比,函数组件更简洁,在引入Hooks之前没有自己的状态,也没有生命周期钩子,在React V16.8版本引入Hooks之后,函数组件能够使用状态以及其他的React特性了

1
2
3
4
5
6
function App(){
const [count,setCount] = React.useState(0)
return <div>
我是App组件
</div>
}

React生命周期

  1. React在V16.3版本时提出了新的生命周期钩子,这意味着旧的生命周期钩子开始弃用,在旧的生命周期中主要弃用了“componentWillMount””coponentWillReceiveProps””componentWillUpdate”这三个生命周期钩子,新增了

    “getDrivedStateFromProps””getSnapshotBeforeUpdate”这两个生命周期钩子。

  2. 常用的React生命周期钩子也就3个,如下:

1
2
3
4
5
6
7
8
9
class App extends React.Component{
//一般在这些钩子里面做一些初始化的事,如开启定时器、发送网络请求、订阅消息等
ComponentDidMount(){}
//一般在这个钩子里面做一些收尾的工作,如关闭定时器、取消订阅等
ComponentWillUnmount(){}
Render(){
return <div></div>
}
}

react_旧生命周期钩子

react_新生命周期钩子

Question 2:什么是pureComponent组件?

“PureComponent”是React中的一个特殊的组件,它通过浅比较(shallow comparison)自动实现了“shouldComponentUpdate”生命周期钩子。与Component相比,当组件的state或props发生改变时,“pureComponent”会对它们进行浅比较,如果没有变化就不会重新渲染,从而提高了组件的性能。