cari

Rumah  >  Soal Jawab  >  teks badan

将Memasukkan tatasusunan sebagai kebergantungan dalam useEffect

Terdapat beberapa data yang masuk daripada tinjauan panjang setiap 5 saat dan saya mahu komponen saya menghantar operasi setiap kali item tatasusunan (atau panjang tatasusunan itu sendiri) berubah. Bagaimanakah cara saya menghalang useEffect daripada masuk ke gelung tak terhingga apabila menghantar tatasusunan sebagai kebergantungan, tetapi masih dapat menjadualkan beberapa operasi jika ada perubahan nilai?

useEffect(() => {
  console.log(outcomes)
}, [outcomes])

di mana outcomes 是一个 ID 数组,例如 [123, 234, 3212]。数组中的项目可能会被替换或删除,因此数组的总长度可能(但不一定)保持不变,因此传递 outcomes.length sebagai tanggungan tidak berlaku.

outcomes Pemilih tersuai daripada pemilihan semula:

const getOutcomes = createSelector(
  someData,
  data => data.map(({ outcomeId }) => outcomeId)
)


P粉748218846P粉748218846404 hari yang lalu576

membalas semua(2)saya akan balas

  • P粉464208937

    P粉4642089372023-10-18 15:49:11

    Menggunakan JSON.stringify() atau mana-mana kaedah perbandingan mendalam mungkin kurang cekap, jika anda mengetahui bentuk objek lebih awal, anda boleh menulis cangkuk kesan anda sendiri untuk mencetuskan panggilan balik ke fungsi kesamaan tersuai anda berdasarkan hasilnya.

    useEffect 的工作原理是检查依赖项数组中的每个值是否与前一渲染中的值相同,如果其中一个不是,则执行回调。因此,我们只需要使用 useRef 保留我们感兴趣的数据实例,并且仅在自定义相等性检查返回 false Tetapkan kejadian baharu untuk mencetuskan kesan.

    function arrayEqual(a1: any[], a2: any[]) {
      if (a1.length !== a2.length) return false;
      for (let i = 0; i < a1.length; i++) {
        if (a1[i] !== a2[i]) {
          return false;
        }
      }
      return true;
    }
    
    type MaybeCleanUpFn = void | (() => void);
    
    function useNumberArrayEffect(cb: () => MaybeCleanUpFn, deps: number[]) {
      const ref = useRef(deps);
    
      if (!arrayEqual(deps, ref.current)) {
        ref.current = deps;
      }
    
      useEffect(cb, [ref.current]);
    }
    

    Penggunaan

    function Child({ arr }: { arr: number[] }) {
      useNumberArrayEffect(() => {
        console.log("run effect", JSON.stringify(arr));
      }, arr);
    
      return 
    {JSON.stringify(arr)}
    ; }

    Melangkah lebih jauh, kami juga boleh menggunakan semula cangkuk ini dengan mencipta cangkuk kesan yang menerima fungsi kesamaan tersuai.

    type MaybeCleanUpFn = void | (() => void);
    type EqualityFn = (a: DependencyList, b: DependencyList) => boolean;
    
    function useCustomEffect(
      cb: () => MaybeCleanUpFn,
      deps: DependencyList,
      equal?: EqualityFn
    ) {
      const ref = useRef(deps);
    
      if (!equal || !equal(deps, ref.current)) {
        ref.current = deps;
      }
    
      useEffect(cb, [ref.current]);
    }
    

    Penggunaan

    useCustomEffect(
      () => {
        console.log("run custom effect", JSON.stringify(arr));
      },
      [arr],
      (a, b) => arrayEqual(a[0], b[0])
    );
    

    Demonstrasi secara langsung

    balas
    0
  • P粉662802882

    P粉6628028822023-10-18 12:32:21

    Anda boleh lulus JSON.stringify(outcomes) sebagai senarai tanggungan:

    Ketahui lebih lanjut di sini

    useEffect(() => {
      console.log(outcomes)
    }, [JSON.stringify(outcomes)])

    balas
    0
  • Batalbalas