प्रतिक्रिया बैच अद्यतन

सिंगल रेंडर कॉल में स्टेट अपडेट को कैसे मिलाएं

React.js बैच अपडेट

आप पहले से ही जानते हैं कि जब भी आप किसी घटक की स्थिति को अपडेट करते हैं, तो रिएक्ट का भिन्न एल्गोरिथ्म वर्चुअल DOM में परिवर्तनों का पता लगाएगा और आपके घटक को वास्तविक DOM में प्रस्तुत करेगा। लेकिन क्या यह वास्तव में हर एक राज्य-अद्यतन के लिए होता है? या रिएक्ट उन अद्यतनों को बैचने का एक तरीका प्रदान करता है, ताकि एकाधिक राज्य उत्परिवर्तन एक ही रेंडर कॉल में संयुक्त हो जाएं?

सिंथेटिक इवेंट बैच अपडेट की अनुमति देते हैं

रिएक्ट 17 और निचला उन अद्यतनों को बैचने के लिए एक तंत्र प्रदान करता है। कोडिंग करते समय आपको वास्तव में इसके बारे में ज्यादा सोचने की जरूरत नहीं है, लेकिन यह जानना कि रिएक्ट आपके कोड को कैसे अनुकूलित कर सकता है, फिर भी एक महान सीख है।

यहाँ क्या हो रहा है।

  • कॉलबैक के भीतर कई राज्य उत्परिवर्तनों को बुलाया जाता है
  • यदि कॉलबैक सिंथेटिक घटना से जुड़ा हुआ है, तो प्रतिक्रिया उन उत्परिवर्तनों को बैच देगी
  • जब म्यूटेशन बैच किए जाते हैं, तो केवल एक रेंडर-कॉल किया जाता है
  • अन्यथा, प्रत्येक उत्परिवर्तन एक नए प्रतिपादन की ओर ले जाता है

बैचिंग की अनुमति देने के लिए, आपके राज्य उत्परिवर्तन को सिंथेटिक रिएक्ट-इवेंट के अंदर बुलाया जाना चाहिए। एक त्वरित अनुस्मारक के रूप में, सिंथेटिक रिएक्ट इवेंट मूल रूप से सभी ब्राउज़रों में समान कार्यक्षमता प्रदान करने के लिए मूल HTML-ईवेंट के आसपास सिर्फ एक आवरण है। प्रत्येक सिंथेटिक ईवेंट हैंडलर को सीधे प्रोप के रूप में एक घटक को प्रदान किया जा सकता है।

यह सब क्रिया में देखने के लिए, यहां एक उदाहरण कोड है जो रिएक्ट को सभी राज्य म्यूटेशनों को एक रेंडर में एक रेंडर में संयोजित करने की अनुमति देगा, बजाय एक रेंडर प्रति म्यूटेशन के।

function Component() {
  const [id, setId] = useState(0);
  const [date, setDate] = useState(new Date());
  const [random, setRandom] = useState(Math.random());

  // A lame callback, but it's just for
  // the demo. Note that clicking on the
  // button will only lead to a single
  // re-render!
  //
  // This is b/c the callback is provided to
  // 'onClick', a synthetic event.
  const onButtonClick = () => {
    setDate(new Date());
    setId(prevId => prevId + 1);
  }
  
  console.log("Render:", id, date);

  return (
    <div>
      <button 
        onClick={onButtonClick}>
        Update state
      </button>
    </div>
  );
}
//
// Almost the same as the previous
// example, but this time w/o
// a batched upate call.
//

function Component() {
  const [id, setId] = useState(0);
  const [date, setDate] = useState(new Date());
  const [random, setRandom] = useState(Math.random());

  // No batching, as the state
  // mutations happend inside
  // a setTimeout - even though
  // the timeout is inside a 
  // synthetic event.
  const onButtonClick = () => {
    setTimeout(() => {
      setDate(new Date());
      setId(prevId => prevId + 1);
    }, 0);
  }
  
  console.log("Render:", id, date);

  return (
    <div>
      <button 
        onClick={onButtonClick}>
        Update state
      </button>
    </div>
  );
}

रिएक्ट 18 और बाद के अपडेट के लिए बैच अपडेट

प्रतिक्रिया के अगले संस्करण के साथ (कम से कम जब मैं इसे लिख रहा हूं), बैचिंग-तंत्र में और सुधार होगा। सिंथेटिक घटनाओं में केवल संभव होने के बजाय, अन्य प्रकार के कॉलबैक भी प्रयोग योग्य होंगे।

  • समय समाप्ति
  • वादे
  • नेटिव इवेंट हैंडलर

इस बदलाव से आपके ऐप के बेहतर प्रदर्शन की संभावना है, क्योंकि कम रेंडरिंग अपने आप हो जाएगी।

रिएक्ट 18 और बाद में बैच अपडेट से बचना

रिएक्ट 18 से शुरू होकर, आपके पास प्रत्येक राज्य उत्परिवर्तन के साथ एक नया रेंडर स्पष्ट रूप से ट्रिगर करने का विकल्प होगा, इसलिए बैच अपडेट से बचना चाहिए। यह संभवतः केवल किनारे के मामलों में उपयोग किया जाएगा, लेकिन फिर भी यह जानना दिलचस्प है।

//  
// This example is almost
// 1:1 from Dan Abramov's
// example.
//
// Use 'flushSync' from the
// 'react-dom'-package.
import { flushSync } from 'react-dom'; 

function handleClick() {
  flushSync(() => {
    setId(prevId => prevId + 1);
  });
  // React has updated the DOM by now
  flushSync(() => {
    setDate(new Date());
  });
  // React has updated the DOM by now
}

सुझाव

संबंधित

परिशिष्ट

भाषाएँ