রিয়েট ইউজেএফেক্টের সাথে লোডিং ফাংশনটিকে কীভাবে কল করবেন only


205

UseEffect প্রতিক্রিয়া হুক যে পরিবর্তনের উপর ফাংশন পাস চালানো হবে। পছন্দসই বৈশিষ্ট্যগুলি পরিবর্তিত হলেই এটি কল করতে উপযুক্ত হতে পারে।

যদি আমি কোনও প্রাথমিক সূচনা ফাংশন থেকে componentDidMountকল করতে চাই এবং পরিবর্তনগুলিতে আবার কল না করি তবে কী হবে? ধরা যাক আমি একটি সত্তা লোড করতে চাই, তবে লোডিং ফাংশনটির জন্য উপাদানটি থেকে কোনও ডেটা প্রয়োজন হয় না। useEffectহুক ব্যবহার করে আমরা এটি কীভাবে তৈরি করতে পারি ?

class MyComponent extends React.PureComponent {
    componentDidMount() {
        loadDataOnlyOnce();
    }
    render() { ... }
}

হুকের সাহায্যে এটি দেখতে এরকম হতে পারে:

function MyComponent() {
    useEffect(() => {
        loadDataOnlyOnce(); // this will fire on every change :(
    }, [...???]);
    return (...);
}

উত্তর:


390

আপনি যদি useEffectপ্রাথমিক রেন্ডারের পরে প্রদত্ত ফাংশনটি চালাতে চান তবে আপনি দ্বিতীয় আর্গুমেন্ট হিসাবে খালি অ্যারে দিতে পারেন।

function MyComponent() {
  useEffect(() => {
    loadDataOnlyOnce();
  }, []);

  return <div> {/* ... */} </div>;
}

27
বিকল্প হিসাবে যদি আপনার কাছে ডেটা আনার জন্য ব্যবহার করা প্যারাম থাকে (যেমন একটি ব্যবহারকারী আইডি) আপনি সেই অ্যারেতে ব্যবহারকারী আইডি পাস করতে পারেন এবং যদি উপাদানটি পরিবর্তন করা হয় তবে ডেটা পুনরায় পাঠানো হবে। অনেকগুলি ব্যবহারের ক্ষেত্রে এটি কাজ করবে।
trixn

4
হ্যাঁ ... স্কিপিং সম্পর্কে আরও তথ্য এখানে নথিভুক্ত করা হয়েছে: reactjs.org/docs/…
মেলোনেক

এই সহজ উত্তর মত মনে হয়, কিন্তু ESLint অভিযোগ ... এই থ্রেডে অন্যান্য উত্তর দেখার stackoverflow.com/a/56767883/1550587
সাইমন হাচিসন

নির্ভরতা অ্যারেতে কেবল লোডডাটাঅনলিঅন পাস করুন। ওইটা কি কাজ করে?
jpmark

85

টি এল; ডিআর

useEffect(yourCallback, []) - প্রথম রেন্ডারের পরেই কলব্যাক ট্রিগার করবে।

বিস্তারিত ব্যাখ্যা

useEffectপ্রতিটি পরে ডিফল্ট দ্বারা চালিতউপাদানটির রেন্ডার (ফলে একটি প্রভাব তৈরি করে)।

রাখার সময় useEffectআপনার উপাদান করার সময় আপনি প্রতিক্রিয়া জানান আপনি একটি প্রভাব হিসাবে কলব্যাক চালাতে চান। প্রতিক্রিয়া রেন্ডারিংয়ের পরে এবং DOM আপডেটগুলি সম্পাদন করার পরে প্রভাবটি চালায়।

যদি আপনি কেবল একটি কলব্যাক পাস করেন - প্রতিটি রেন্ডার পরে কলব্যাক চলবে।

যদি দ্বিতীয় আর্গুমেন্ট (অ্যারে) পাস করা হয় তবে প্রতিক্রিয়াটি প্রথম রেন্ডারের পরে কলব্যাক চালাবে এবং প্রতিবার অ্যারেতে থাকা উপাদানগুলির মধ্যে একটি পরিবর্তন করা হবে। উদাহরণস্বরূপ যখন স্থাপন useEffect(() => console.log('hello'), [someVar, someOtherVar])- কলব্যাক প্রথম রেন্ডার চালানো হবে এবং কোন পর রেন্ডার যে এক someVarবা someOtherVarপরিবর্তিত হয়।

দ্বিতীয় আর্গুমেন্টকে খালি অ্যারে দিয়ে যাওয়ার পরে, প্রতিক্রিয়াটি প্রতিটি অ্যারে রেন্ডার করার পরে তুলনা করবে এবং দেখবে কিছুই পরিবর্তন করা হয়নি, সুতরাং প্রথম রেন্ডারের পরে কলব্যাককে কল করে।


68

ব্যবহারমাউন্টএফেক্ট হুক

কম্পোনেন্ট মাউন্টগুলির পরে একবার কোনও ক্রিয়াকলাপ চালানো এমন একটি সাধারণ প্যাটার্ন যা এটি তার নিজের একটি হুককে ন্যায্যতা দেয় যা প্রয়োগের বিশদটি গোপন করে।

const useMountEffect = (fun) => useEffect(fun, [])

এটি কোনও কার্যকরী উপাদান ব্যবহার করুন।

function MyComponent() {
    useMountEffect(function) // function will run only once after it has mounted. 
    return <div>...</div>;
}

ইউজমাউন্টএফেক্ট হুক সম্পর্কে

useEffectদ্বিতীয় অ্যারের আর্গুমেন্টের সাথে ব্যবহার করার সময় , প্রতিক্রিয়াটি মাউন্টিং (প্রাথমিক রেন্ডার) এবং অ্যারেতে মান পরিবর্তনের পরে কলব্যাক চালাবে run যেহেতু আমরা একটি খালি অ্যারে পাস করি, এটি কেবল মাউন্ট করার পরে চলবে।


19
আমি আপনার উত্তরটিকে অত্যন্ত পছন্দ করি, কারণ ESLint নিয়ম "রিঅ্যাক্ট-হুকস / এক্সপোসিটিভ-ডিপস" সর্বদা ফাঁকা নির্ভরতার তালিকায় ব্যর্থ হবে। এবং উদাহরণস্বরূপ বিখ্যাত তৈরি-প্রতিক্রিয়া-অ্যাপ্লিকেশন টেম্পলেটটি সেই নিয়মটি প্রয়োগ করবে।
ডায়নালন

1
সম্পূর্ণরূপে @ ডায়নালনের সাথে একমত এটি গ্রহণযোগ্য সমাধান হওয়া উচিত কারণ এটি ESLint নিয়মে হস্তক্ষেপ করে না
মিকাদো 68

ধন্যবাদ @ ডিনালন এবং মিকাদো 68 :-)। সিদ্ধান্তটি ওপি-র একটি বিশেষাধিকার। আপনার মন্তব্য সম্পর্কে আমাকে অবহিত করা হয়েছিল, কিন্তু ওপিটি ছিল না। প্রশ্নটিতে সরাসরি মন্তব্য করে আপনি এটি তাকে পরামর্শ দিতে পারেন।
বেন কার্প

2
এখন আপনি useMountযখন আপনার এফেক্ট ফাংশনটির প্রপস থেকে কিছু প্রয়োজন হয় তা ব্যবহার করতে পারেন তবে লিটারার সতর্কতা ছাড়াই যদি সেই মান পরিবর্তন হয় তবে আবার চালানোর দরকার নেই: useEffect(()=>console.log(props.val),[])নির্ভরতা সতর্কতা হারিয়ে useMount(()=>console.log(props.val))ফেলবে তবে একটি সতর্কতা তৈরি করবে না তবে "কাজ করে"। যদিও সমবর্তী মোডে সমস্যা হবে কিনা তা আমি নিশ্চিত নই।
এইচএমআর

1
আমি এটি পছন্দ করি :) পূর্ববর্তী রাষ্ট্র হিসাবে একই কারণ; ইএসলিন্ট নিয়মটি এ সম্পর্কে কোনও অভিযোগ করবে না, এটির নামটি খালি অ্যারের চেয়ে বোঝা আরও সহজ
ফ্রেক্সজ

20

দ্বিতীয় আর্গুমেন্ট হিসাবে একটি খালি অ্যারে পাস করুন useEffect। এটি ডক্সগুলি উদ্ধৃত করে কার্যকরভাবে প্রতিক্রিয়া জানায় :

এটি প্রতিক্রিয়া জানায় যে আপনার প্রভাব প্রপস বা রাজ্যের কোনও মানের উপর নির্ভর করে না, তাই এটি পুনরায় চালানোর দরকার হয় না।

এখানে একটি স্নিপেট রয়েছে যা আপনি এটি চালানোর জন্য চালাতে পারেন যে এটি কাজ করে:

function App() {
  const [user, setUser] = React.useState(null);

  React.useEffect(() => {
    fetch('https://randomuser.me/api/')
      .then(results => results.json())
      .then(data => {
        setUser(data.results[0]);
      });
  }, []); // Pass empty array to only run once on mount.
  
  return <div>
    {user ? user.name.first : 'Loading...'}
  </div>;
}

ReactDOM.render(<App/>, document.getElementById('app'));
<script src="https://unpkg.com/react@16.7.0-alpha.0/umd/react.development.js"></script>
<script src="https://unpkg.com/react-dom@16.7.0-alpha.0/umd/react-dom.development.js"></script>

<div id="app"></div>


4

আমি কোনও mountফাংশন সংজ্ঞায়িত করতে চাই , এটি এসিলিন্টকে একইভাবে চালিত useMountকরে এবং আমি এটি আরও স্ব-ব্যাখ্যামূলক বলে মনে করি।

const mount = () => {
  console.log('mounted')
  // ...

  const unmount = () => {
    console.log('unmounted')
    // ...
  }
  return unmount
}
useEffect(mount, [])

0

কৌশলটি হ'ল ইউজএফেক্টটি দ্বিতীয় প্যারামিটার নেয়।

দ্বিতীয় প্যারামটি ভেরিয়েবলগুলির একটি অ্যারে যা উপাদানটি পুনরায় রেন্ডারিংয়ের আগে এটি পরিবর্তন হয়েছে তা নিশ্চিত করার জন্য উপাদানটি যাচাই করবে। আপনি এখানে যা কিছু প্রপস এবং স্টেট চান তার বিপরীতে পরীক্ষা করতে পারেন।

অথবা, কিছুই রাখবেন না:

import React, { useEffect } from 'react';

function App() {
  useEffect(() => {

    // Run! Like go get some data from an API.

  }, []); //Empty array as second argument

  return (
    <div>
      {/* Do something with data. */}
    </div>
  );
}

এটি নিশ্চিত করবে যে কেবল একবার ব্যবহারটি কার্যকর হবে।

দস্তাবেজগুলি থেকে নোট:

আপনি যদি এই অপটিমাইজেশন ব্যবহার করেন তবে নিশ্চিত হয়ে নিন যে অ্যারেতে উপাদান ব্যবস্থার সমস্ত মান (যেমন প্রপস এবং রাজ্য) অন্তর্ভুক্ত রয়েছে যা সময়ের সাথে সাথে পরিবর্তিত হয় এবং যা প্রভাব দ্বারা ব্যবহৃত হয়। অন্যথায়, আপনার কোড পূর্ববর্তী রেন্ডারগুলির থেকে বাসি মানগুলি উল্লেখ করবে।


3
যদি আপনার সিএসএস ট্রিক্স থেকে আক্ষরিক অনুলিপি / আটকানো হয় তবে আপনার উত্সটি জমা দেওয়া আপনার পক্ষে কমপক্ষে। css-tricks.com/run-useeffect-only-once
বার্তিশিয়ান
আমাদের সাইট ব্যবহার করে, আপনি স্বীকার করেছেন যে আপনি আমাদের কুকি নীতি এবং গোপনীয়তা নীতিটি পড়েছেন এবং বুঝতে পেরেছেন ।
Licensed under cc by-sa 3.0 with attribution required.