>웹 프론트엔드 >JS 튜토리얼 >React의 setState 요약

React의 setState 요약

angryTom
angryTom앞으로
2019-12-19 17:10:563070검색

React의 setState 요약

react의 setState 메소드는 비동기식인가요 동기식인가요? 실제로 어떤 조건에 따라 비동기식과 동기식으로 구분되나요?

1 먼저 반응 구성 요소에서 상태를 변경하는 여러 가지 방법을 살펴보겠습니다.


import React, { Component } from 'react'class Index extends Component {
    state={
        count:1
    }
    test1 = () => {        // 通过回调函数的形式
        this.setState((state,props)=>({
            count:state.count+1
        }));
        console.log('test1 setState()之后',this.state.count);
    }
    test2 = () => {        // 通过对象的方式(注意:此方法多次设置会合并且只调用一次!)
        this.setState({
            count:this.state.count+1
        });
        console.log('test2 setState()之后',this.state.count);
    }
    test3 = () => {        // 不能直接修改state的值,此方法强烈不建议!!!因为不会触发重新render
        this.state.count += 1;
    }
    test4 = () => {        // 在第二个callback拿到更新后的state
        this.setState({
            count:this.state.count+1
        },()=>{// 在状态更新且页面更新(render)后执行
            console.log('test4 setState()之后',this.state.count);
        });
    }
    render() {
        console.log('render');        
        return (            
        <p>
                <h1>currentState:{this.state.count}</h1>
                <button onClick={this.test1}>测试1</button>
                <button onClick={this.test2}>测试2</button>
                <button onClick={this.test3} style={{color:&#39;red&#39;}}>测试3</button>
                <button onClick={this.test4}>测试4</button>
            </p>        )
    }
}
export default Index;

2. SetState()는 상태를 비동기식 또는 동기식으로 업데이트합니다.

setState가 있는 위치를 결정해야 합니다. 실행됨

동기화: react에 의해 제어되는 콜백 함수에서: 수명 주기 후크/반응 이벤트 수신 콜백


import React, { Component } from &#39;react&#39;class Index extends Component {
    state={
        count:1
    }    /* 
    react事件监听回调中,setState()是异步状态    */
    update1 = () => {
        console.log(&#39;update1 setState()之前&#39;,this.state.count);        
        this.setState((state,props)=>({
            count:state.count+1
        }));
        console.log(&#39;update1 setState()之后&#39;,this.state.count);
    }    /* 
    react生命周期钩子中,setState()是异步更新状态    */
    componentDidMount() {
        console.log(&#39;componentDidMount setState()之前&#39;,this.state.count);        
        this.setState((state,props)=>({
            count:state.count+1
        }));
        console.log(&#39;componentDidMount setState()之后&#39;,this.state.count);
    }
    
    render() {
        console.log(&#39;render&#39;);        
        return (            
        <p>
                <h1>currentState:{this.state.count}</h1>
                <button onClick={this.update1}>测试1</button>
                <button onClick={this.update2}>测试2</button>
            </p>        )
    }
}
export default Index;

비동기화: non-react에 의해 제어되는 비동기 콜백 함수에서: 타이머 콜백/네이티브 이벤트 콜백 수신/ Promise


import React, { Component } from &#39;react&#39;class Index extends Component {
    state={
        count:1
    }    /* 
    定时器回调    */
    update1 = () => {
        setTimeout(()=>{
            console.log(&#39;setTimeout setState()之前&#39;,this.state.count);//1
            this.setState((state,props)=>({
                count:state.count+1
            }));
            console.log(&#39;setTimeout setState()之后&#39;,this.state.count);//2        
            });
    }    /* 
    原生事件回调    */
    update2 = () => {
        const h1 = this.refs.count;
        h1.onclick = () => {
            console.log(&#39;onClick setState()之前&#39;,this.state.count);//1
            this.setState((state,props)=>({
                count:state.count+1
            }));
            console.log(&#39;onClick setState()之后&#39;,this.state.count);//2        
            }
    }    /* 
    Promise回调    */
    update3 = () => {
        Promise.resolve().then(value=>{
            console.log(&#39;Promise setState()之前&#39;,this.state.count);//1
            this.setState((state,props)=>({
                count:state.count+1
            }));
            console.log(&#39;Promise setState()之后&#39;,this.state.count);//2        
            });
    }
    
    render() {
        console.log(&#39;render&#39;);        return (            
        <p>
                <h1 ref=&#39;count&#39;>currentState:{this.state.count}</h1>
                <button onClick={this.update1}>测试1</button>
                <button onClick={this.update2}>测试2</button>
                <button onClick={this.update3}>测试3</button>
            </p>        )
    }
}
export default Index;

3. setState()에 대한 다중 호출 관련 문제:

Asynchronous setState()

(1) 다중 호출, 처리 방법:

setState({}): merge 상태를 한 번 업데이트하려면 render()를 한 번만 호출하여 인터페이스를 업데이트하세요. 여러 호출이 하나로 병합되고 이후 값이 이전 값을 덮어씁니다.

setState(fn): 상태를 여러 번 업데이트합니다. 인터페이스를 업데이트하려면 render()를 한 번만 호출하세요. 여러 번 호출하면 하나로 병합되지 않으며 후속 값은 이전 값을 덮어씁니다.


import React, { Component } from &#39;react&#39;class Index extends Component {
    state={
        count:1
    }
    update1 = () => {
        console.log(&#39;update1 setState()之前&#39;,this.state.count);        
        this.setState((state,props)=>({
            count:state.count+1
        }));
        console.log(&#39;update1 setState()之后&#39;,this.state.count);
        console.log(&#39;update1 setState()之前2&#39;,this.state.count);        
        this.setState((state,props)=>({
            count:state.count+1
        }));
        console.log(&#39;update1 setState()之后2&#39;,this.state.count);
    }
    update2 = () => {
        console.log(&#39;update2 setState()之前&#39;,this.state.count);        
        this.setState({
            count:this.state.count+1
        });
        console.log(&#39;update2 setState()之后&#39;,this.state.count);
        console.log(&#39;update2 setState()之前2&#39;,this.state.count);        
        this.setState({
            count:this.state.count+1
        });
        console.log(&#39;update2 setState()之后2&#39;,this.state.count);
    }
    update3 = () => {
        console.log(&#39;update3 setState()之前&#39;,this.state.count);        
        this.setState({
            count:this.state.count+1
        });
        console.log(&#39;update3 setState()之后&#39;,this.state.count);
        console.log(&#39;update3 setState()之前2&#39;,this.state.count);        
        this.setState((state,props)=>({
            count:state.count+1
        }));// 这里需要注意setState传参为函数模式时,state会确保拿到的是最新的值
        console.log(&#39;update3 setState()之后2&#39;,this.state.count);
    }
    update4 = () => {
        console.log(&#39;update4 setState()之前&#39;,this.state.count);        
        this.setState((state,props)=>({
            count:state.count+1
        }));
        console.log(&#39;update4 setState()之后&#39;,this.state.count);
        console.log(&#39;update4 setState()之前2&#39;,this.state.count);        
        this.setState({
            count:this.state.count+1
        });// 这里需要注意的是如果setState传参为对象且在最后,那么会与之前的setState合并
        console.log(&#39;update4 setState()之后2&#39;,this.state.count);
    }
    render() {
        console.log(&#39;render&#39;);        return (            
        <p>
                <h1>currentState:{this.state.count}</h1>
                <button onClick={this.update1}>测试1</button>
                <button onClick={this.update2}>测试2</button>
                <button onClick={this.update3}>测试3</button>
                <button onClick={this.update4}>测试4</button>
            </p>        )
    }
}
export default Index;

(2) setState 비동기 업데이트 후 상태 데이터를 얻는 방법:

setState()의 콜백 함수에서

4. 일반적인 setState 인터뷰 질문(setState 실행 순서)


import React, { Component } from &#39;react&#39;// setState执行顺序class Index extends Component {
    state={
        count:0
    }
    componentDidMount() {        this.setState({count:this.state.count+1});        
    this.setState({count:this.state.count+1});
        console.log(this.state.count);// 2 => 0
        this.setState(state=>({count:state.count+1}));        
        this.setState(state=>({count:state.count+1}));
        console.log(this.state.count);// 3 => 0
        setTimeout(() => {            
        this.setState({count:this.state.count+1});
            console.log(&#39;setTimeout&#39;,this.state.count);// 10 => 6
            this.setState({count:this.state.count+1});
            console.log(&#39;setTimeout&#39;,this.state.count);// 12 => 7        
            });
        Promise.resolve().then(value=>{            
        this.setState({count:this.state.count+1});
            console.log(&#39;Promise&#39;,this.state.count);// 6 => 4
            this.setState({count:this.state.count+1});
            console.log(&#39;Promise&#39;,this.state.count);// 8 => 5        
            });
    }
    render() {
        console.log(&#39;render&#39;,this.state.count);// 1 => 0  // 4 => 3 // 5 => 4 // 7 => 5 // 9 => 6 // 11 => 7
        return (            <p>
                <h1>currentState:{this.state.count}</h1>
                <button onClick={this.update1}>测试1</button>
                <button onClick={this.update2}>测试2</button>
                <button onClick={this.update3}>测试3</button>
                <button onClick={this.update4}>测试4</button>
            </p>        )
    }
}
export default Index;

요약: 상태를 업데이트하기 위해 반응으로 setState()를 작성하는 2가지 방법

1) setState(updater, [callback])

updater: stateChange 객체를 반환하는 함수: (state, props)=> stateChange, 수신된

state 및 props는 최신임이 보장됩니다. 2) setState(stateChange, [callback])

stateChange는 객체이고, callback은

상태가 업데이트된 후에만 실행되는 선택적 콜백 함수입니다. 인터페이스가 업데이트됩니다

참고:

Object는 function method의 약어입니다.

새 상태가 원래 상태에 의존하지 않으면 객체 메소드를 사용하세요.

새 상태가

setState() 이후 최신 상태 데이터를 가져와서 두 번째 콜백 함수에서 가져와야 하는 경우

이 기사는

js 튜토리얼

칼럼에서 가져온 것입니다. 환영합니다!

위 내용은 React의 setState 요약의 상세 내용입니다. 자세한 내용은 PHP 중국어 웹사이트의 기타 관련 기사를 참조하세요!

성명:
이 기사는 cnblogs.com에서 복제됩니다. 침해가 있는 경우 admin@php.cn으로 문의하시기 바랍니다. 삭제