इसका उपयोग करते समय क्या होता है। प्रतिक्रिया घटक में कई बार शुरू करें।


101

मैं यह जांचना चाहता था कि जब आप इस का उपयोग करते हैं तो क्या होता है। कई बार (चर्चा के लिए 2 बार) शुरू करें। मैंने सोचा था कि घटक दो बार प्रस्तुत किया जाएगा, लेकिन जाहिर है कि यह केवल एक बार प्रदान किया गया है। मुझे एक और उम्मीद थी कि शायद सेटस्टेट के लिए दूसरा कॉल पहले वाले से अधिक होगा, लेकिन आपने अनुमान लगाया - ठीक काम किया।

एक JSfiddle लिंक

var Hello = React.createClass({
  render: function() {
    return (
      <div>
        <div>Hello {this.props.name}</div>
        <CheckBox />
      </div>
    );
  }
});

var CheckBox = React.createClass({
  getInitialState: function() {
    return {
      alex: 0
    };
  },

  handleChange: function(event) {
    this.setState({
      value: event.target.value
    });
    this.setState({
      alex: 5
    });
  },

  render: function() {
    alert('render');
    return (
      <div>
        <label htmlFor="alex">Alex</label>
        <input type="checkbox" onChange={this.handleChange} name="alex" />
        <div>{this.state.alex}</div>
      </div>
    );
  }
});

ReactDOM.render(
  <Hello name="World" />,
  document.getElementById('container')
);

जैसा कि आप देखेंगे, एक अलर्ट जो कहता है कि 'रेंडर' हर रेंडर पर पॉप अप करता है।

क्या आपके पास इसका स्पष्टीकरण है कि यह क्यों ठीक से काम करता है?


2
प्रतिक्रिया बहुत चालाक है और केवल तभी फिर से प्रस्तुत करना होगा जब राज्य को प्रस्तुत करना आवश्यक हो। अपने रेंडर विधि में आप केवल उपयोग कर रहे हैं this.state.alex- यदि आप एक तत्व जोड़ते हैं तो क्या होता है this.state.value?
मार्टिन वेन्विच

1
@MartinWedvich अगर मैं इस पर निर्भर हूं तो यह टूट जाएगा। इसके लिए आपके पास 'getInitialState' विधि है - डिफ़ॉल्ट मान सेट करने के लिए ताकि आपका ऐप टूट न जाए।
एलेक्जेंडर

1
संबंधित और उपयोगी: stackoverflow.com/questions/48563650/…
andydavies

जवाबों:


116

प्रतिक्रिया बैच अद्यतन राज्य अद्यतन जो ईवेंट हैंडलर और जीवनचक्र विधियों में होता है। इस प्रकार, यदि आप एक <div onClick />हैंडलर में कई बार स्टेट्स अपडेट करते हैं, तो रिएक्ट री-रेंडरिंग से पहले इवेंट हैंडलिंग का इंतजार करेगा।

स्पष्ट होने के लिए, यह केवल रिएक्ट-नियंत्रित सिंथेटिक इवेंट हैंडलर और जीवनचक्र विधियों में काम करता है। setTimeoutउदाहरण के लिए AJAX और ईवेंट हैंडलर्स में स्टेट अपडेट्स को बैचेन नहीं किया गया है ।


1
धन्यवाद, यह समझ में आता है, किसी भी विचार यह कैसे पर्दे के पीछे किया जाता है?
एलेक्जेंडर

13
चूंकि रिएक्ट सिंथेटिक इवेंट हैंडलर (जैसे <div onClick />) और घटक जीवन चक्र विधियों को पूरी तरह से नियंत्रित करता है , इसलिए यह जानता है कि यह setStateकॉल की अवधि के लिए व्यवहार को सुरक्षित रूप से बैच स्टेट अपडेट में बदल सकता है और फ्लश की प्रतीक्षा कर सकता है। इसके setTimeoutविपरीत AJAX या हैंडलर में, रिएक्ट के पास यह जानने का कोई तरीका नहीं है कि हमारे हैंडलर ने कब निष्पादित किया है। तकनीकी रूप से, रिएक्ट कतार दोनों मामलों में अपडेट करता है, लेकिन तुरंत रिएक्ट-नियंत्रित हैंडलर के बाहर फ्लश करता है।
क्रिस गौडरु

1
@neurosnap मुझे नहीं लगता कि डॉक्स इस पर बहुत विस्तार से जाते हैं। यह राज्य और जीवनचक्र अनुभाग और सेटस्टेट डॉक्स में सारगर्भित हैReactDefaultBatchingStrategy के लिए कोड देखें , जो वर्तमान में एकमात्र आधिकारिक बैचिंग रणनीति है।
क्रिस गौड्रेउ

2
@BenjaminToueg मेरा मानना ​​है कि आप उपयोग कर सकते हैं ReactDOM.unstable_batchedUpdates(function)setState रिएक्ट इवेंट हैंडलर्स के बाहर बैचने के लिए । जैसा कि नाम से ही स्पष्ट है, आप अपनी वारंटी को रद्द कर देंगे।
क्रिस गॉडरू

1
इस आदमी को रेफरी हमेशा अच्छा twitter.com/dan_abramov/status/887963264335872000?lang=en
हर्ट्जेल गिनीज

33

सेटस्टेट () विधि घटक की स्थिति को तुरंत अपडेट नहीं करती है, यह सिर्फ बाद में संसाधित होने के लिए अद्यतन को एक कतार में रखती है। प्रतिक्रिया अधिक कुशल बनाने के लिए एक साथ कई अद्यतन अनुरोधों को बैच सकती है। इसके कारण, घटक की पिछली स्थिति के आधार पर स्थिति को अपडेट करने का प्रयास करते समय विशेष सावधानी बरतनी चाहिए।

उदाहरण के लिए, निम्न कोड केवल राज्य मूल्य विशेषता को 1 से बढ़ाएगा, भले ही इसे 4 बार कहा गया हो:

 class Counter extends React.Component{
   constructor(props){
     super(props)
    //initial state set up
     this.state = {value:0}
   }
   componentDidMount(){
    //updating state
    this.setState({value:this.state.value+1})
    this.setState({value:this.state.value+1})
    this.setState({value:this.state.value+1})
    this.setState({value:this.state.value+1})
   }
   render(){
    return <div>Message:{this.state.value}</div>
   }
}

अद्यतन किए जाने के बाद किसी स्थिति का उपयोग करने के लिए, कॉलबैक तर्क में सभी तर्क दें:

//this.state.count is originally 0
this.setState({count:42}, () => {
  console.log(this.state.count)
//outputs 42
})

SetState (updater, [callback]) विधि updater फ़ंक्शन में पिछले राज्य और गुणों के आधार पर स्थिति को अपडेट करने के लिए इसके पहले तर्क के रूप में ले सकती है। Updater फ़ंक्शन का रिटर्न मान पिछले घटक स्थिति के साथ उथले रूप से मर्ज किया जाएगा। विधि राज्य को अतुल्यकालिक रूप से अपडेट करती है, इसलिए एक विकल्प कॉलबैक है जिसे राज्य द्वारा पूरी तरह से अपडेट करने के बाद कॉल किया जाएगा।

उदाहरण:

this.setState((prevState, props) => { 
return {attribute:"value"}
})

पिछली अवस्था के आधार पर राज्य को कैसे अपडेट किया जाए, इसका एक उदाहरण इस प्रकार है:

    class Counter extends React.Component{
      constructor(props) {
        super(props)
    //initial state set up
        this.state = {message:"initial message"}
    }
      componentDidMount() {
    //updating state
        this.setState((prevState, props) => {
          return {message: prevState.message + '!'}
        })
     }
     render(){
       return <div>Message:{this.state.message}</div>
     }
  }

आह, मैं इसके बारे में नहीं जानता था setState(updater,[callback]), यह उस के लिए एक कम क्रिया Object.assignधन्यवाद की तरह है!
एजे वेंचरला

1
@Biboswan, हाय, मैं रिएक्ट में नया हूं और आपसे पूछना चाहता हूं कि क्या यह सच है कि CompountDidMount मेथड के अंदर के सभी चार सेट मर्ज हो गए हैं और केवल LAST सेटस्टैट को अंजाम दिया जाएगा लेकिन अन्य 3 को नजरअंदाज कर दिया जाएगा?
डिकेन्स
हमारी साइट का प्रयोग करके, आप स्वीकार करते हैं कि आपने हमारी Cookie Policy और निजता नीति को पढ़ और समझा लिया है।
Licensed under cc by-sa 3.0 with attribution required.