recherche
Maisoninterface Webjs tutorieluseCustomReducer Hook : un outil de gestion d'état polyvalent

useCustomReducer Hook: A Versatile State Management Tool

Introduction

La gestion de l'état dans React peut être délicate, en particulier lorsqu'il s'agit de structures d'état complexes ou imbriquées. Pour simplifier cela, le hook useCustomReducer combine la puissance de useReducer avec une API flexible pour mettre à jour l'état de manière propre et déclarative. Ce hook prend en charge les états primitifs, imbriqués et matriciels, ce qui le rend adapté à un large éventail de cas d'utilisation.

Dans cet article, nous explorerons le hook useCustomReducer et ses méthodes de base pour gérer l'état dans les applications React. Nous aborderons la définition du hook, ses signatures de méthode et des exemples d'utilisation détaillés pour différents types de structures d'état. À la fin, vous aurez une solide compréhension de la façon d'utiliser le hook useCustomReducer pour gérer les états complexes dans vos composants React.

 Table des matières

  • Présentation
  • Table des matières
  • Aperçu des crochets
  • Exemple de composant React
  • Caractéristiques
  • Définition
    • Définitions des méthodes
  • Exemples d'utilisation détaillés
    • Gérer les primitives
    • Gestion des données du formulaire
    • Gestion des tableaux
    • Gestion de l'état imbriqué
  • Pourquoi utiliser useCustomReducer ?
  • Conclusion
  • Ressources supplémentaires

Présentation des crochets

Le hook useCustomReducer est un hook React personnalisé qui fournit un moyen simple et flexible de gérer des structures d'état complexes. Il combine les avantages de useReducer avec une API propre pour mettre à jour les valeurs d'état. Ce hook est conçu pour gérer différents types d'état, notamment les valeurs primitives, les objets, les tableaux et les structures de données imbriquées.

Voici un aperçu du hook useCustomReducer :

  • Méthodes de base :

    • set : Mettez à jour les valeurs d'état directement ou via une fonction de rappel.
    • réinitialiser : rétablir l'état à sa valeur initiale.
    • fusionner : fusionner les mises à jour partielles dans l'état existant.
  • Structures d'état : - Prend en charge les valeurs primitives (par exemple, les nombres, les chaînes, les booléens). - Gère les structures d'état basées sur les objets (par exemple, les données de formulaire, les profils utilisateur). - Gère les structures d'état basées sur des tableaux (par exemple, listes, collections).

  • Type-Safe : - Entièrement tapé à l'aide de TypeScript pour un développement fiable et une prévention des erreurs.

  • API simple : - Fournit des méthodes intuitives pour mettre à jour, réinitialiser et fusionner les valeurs d'état. - Prend en charge les mises à jour directes et les fonctions de rappel pour les changements d'état dynamiques.

import { useReducer, useCallback, useMemo } from "react";

type Primitive = boolean | string | number | Date | null | undefined;
type NestedObject = { [key: string]: Primitive | NestedObject | NestedArray };
type NestedArray = Array<primitive nestedobject>;

type State = Primitive | NestedObject | NestedArray;

type Action<t> =
  | { type: "SET"; payload: Partial<t> | ((prevState: T) => Partial<t>) }
  | { type: "RESET"; payload?: T }
  | { type: "MERGE"; payload: Partial<t> };

function useCustomReducer<t extends state>(initialState: T) {
  const reducer = useCallback(
    (state: T, action: Action<t>): T => {
      switch (action.type) {
        case "SET":
          const newPayload =
            typeof action.payload === "function"
              ? action.payload(state)
              : action.payload;
          if (newPayload instanceof Date) {
            return newPayload as T;
          }
          if (
            typeof state === "object" &&
            !Array.isArray(state) &&
            state !== null
          ) {
            return { ...state, ...newPayload };
          }
          return newPayload as T;
        case "RESET":
          return action.payload ?? initialState;
        case "MERGE":
          if (
            typeof state === "object" &&
            !Array.isArray(state) &&
            state !== null
          ) {
            return { ...state, ...action.payload };
          }
          return action.payload as T;
        default:
          throw new Error("Invalid action type");
      }
    },
    [initialState]
  );

  const [state, dispatch] = useReducer(reducer, initialState);

  const set = useCallback(
    (payload: Partial<t> | ((prevState: T) => Partial<t>)) =>
      dispatch({ type: "SET", payload }),
    []
  );
  const reset = useCallback(
    (payload?: T) => dispatch({ type: "RESET", payload }),
    []
  );
  const merge = useCallback(
    (payload: Partial<t>) => dispatch({ type: "MERGE", payload }),
    []
  );

  const memoizedState = useMemo(() => state, [state]);

  return [memoizedState, { set, reset, merge }] as const;
}

export default useCustomReducer;
</t></t></t></t></t></t></t></t></t></primitive>

Le hook useCustomReducer est implémenté à l’aide du hook useReducer de React. Il définit une fonction de réduction personnalisée qui gère différents types d'actions pour mettre à jour, réinitialiser ou fusionner les valeurs d'état. Le hook fournit trois méthodes principales définies, réinitialisées et fusionnées pour interagir avec l'état. La méthode set peut accepter soit un objet avec de nouvelles valeurs d'état, soit une fonction de rappel pour calculer l'état suivant. La méthode de réinitialisation ramène l'état à sa valeur initiale, tandis que la méthode de fusion fusionne les mises à jour partielles dans l'état existant.

Exemple de composant React

Voici un exemple d'utilisation du hook useCustomReducer dans un composant React pour gérer un état de compteur simple :

import useCustomReducer from "./use-custom-reducer";
import { faker } from "@faker-js/faker";
import { Button } from "@/components/ui/button";

export default function Use() {
  const [formValues, { set, reset, merge }] = useCustomReducer({
    name: faker.person.firstName(),
    age: faker.number.int({ min: 18, max: 99 }),
    address: {
      street: faker.location.streetAddress(),
      city: faker.location.city(),
      state: faker.location.state(),
      zip: faker.location.zipCode(),
    },
    hobbies: [faker.person.bio(), faker.person.bio(), faker.person.bio()],
  });

  const [bool, { set: setBool }] = useCustomReducer<boolean>(
    faker.datatype.boolean()
  );
  const [num, { set: setNum }] = useCustomReducer(faker.number.int());
  const [str, { set: setStr }] = useCustomReducer<string>(faker.lorem.word());
  const [date, { set: setDate }] = useCustomReducer(faker.date.recent());
  const [nil, { set: setNil }] = useCustomReducer(null);
  const [undef, { set: setUndef }] = useCustomReducer(undefined);
  const [arr, { set: setArr }] = useCustomReducer([
    faker.number.int(),
    faker.number.int(),
    faker.number.int(),
  ]);
  const [nestedArr, { set: setNestedArr }] = useCustomReducer([
    faker.number.int(),
    faker.lorem.word(),
    { three: faker.number.float() },
  ]);

  const [obj, { set: setObj }] = useCustomReducer({
    a: faker.number.int(),
    b: faker.number.int(),
    c: faker.number.int(),
  });
  const [nestedObj, { set: setNestedObj }] = useCustomReducer({
    a: faker.number.int(),
    b: faker.lorem.word(),
    c: { three: faker.number.float() },
  });

  return (
    <div classname="p-4 space-y-6">
      <h1 id="Use">Use</h1>
      <div classname="space-x-2 space-y-2">
        <h2 id="Form-Values">Form Values</h2>
        <p classname="text-gray-500">{JSON.stringify(formValues)}</p>
        <button onclick="{()"> set({ name: faker.person.firstName() })}>
          Set Name
        </button>
        <button onclick="{()"> set((prevState) => ({ age: prevState.age - 1 }))}
        >
          Decrement Age
        </button>
        <button onclick="{()"> set((prevState) => ({ age: prevState.age + 1 }))}
        >
          Increment Age
        </button>
        <button onclick="{()">
            set((prevState) => ({
              address: {
                ...prevState.address,
                street: faker.location.streetAddress(),
              },
            }))
          }
        >
          Set Street
        </button>
        <button onclick="{()"> reset()}>Reset</button>
        <button onclick="{()"> merge({ age: faker.number.int({ min: 18, max: 99 }) })}
        >
          Merge
        </button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="Boolean-Value">Boolean Value</h2>
        <p classname="text-gray-500">{bool.toString()}</p>
        <button onclick="{()"> setBool(faker.datatype.boolean())}>
          Set Bool
        </button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="Number-Value">Number Value</h2>
        <p classname="text-gray-500">{num.toString()}</p>
        <button onclick="{()"> setNum(faker.number.int())}>Set Num</button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="String-Value">String Value</h2>
        <p classname="text-gray-500">{str}</p>
        <button onclick="{()"> setStr(faker.lorem.word())}>Set Str</button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="Date-Value">Date Value</h2>
        <p classname="text-gray-500">{JSON.stringify(date)}</p>
        <button onclick="{()"> setDate(faker.date.recent())}>Set Date</button>
        <button onclick="{()"> setDate(new Date("2022-01-01"))}>
          Set Date to 2022
        </button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="Nil-and-Undefined">Nil and Undefined</h2>
        <p classname="text-gray-500">{String(nil)}</p>
        <button onclick="{()"> setNil(null)}>Set Nil</button>
        <p classname="text-gray-500">{String(undef)}</p>
        <button onclick="{()"> setUndef(undefined)}>Set Undef</button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="Array-Value">Array Value</h2>
        <p classname="text-gray-500">{arr.toString()}</p>
        <button onclick="{()">
            setArr([faker.number.int(), faker.number.int(), faker.number.int()])
          }
        >
          Set Arr
        </button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="Nested-Array">Nested Array</h2>
        <p classname="text-gray-500">{JSON.stringify(nestedArr)}</p>
        <button onclick="{()">
            setNestedArr([
              faker.number.int(),
              faker.lorem.word(),
              { three: faker.number.float() },
            ])
          }
        >
          Set Nested Arr
        </button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="Object-Value">Object Value</h2>
        <p classname="text-gray-500">{JSON.stringify(obj)}</p>
        <button onclick="{()">
            setObj({
              a: faker.number.int(),
              b: faker.number.int(),
              c: faker.number.int(),
            })
          }
        >
          Set Obj
        </button>
      </div>
      <hr classname="border-t border-gray-300">
      <div classname="space-x-2 space-y-2">
        <h2 id="Nested-Object">Nested Object</h2>
        <p classname="text-gray-500">{JSON.stringify(nestedObj)}</p>
        <button onclick="{()">
            setNestedObj({
              a: faker.number.int(),
              b: faker.lorem.word(),
              c: { three: faker.number.float() },
            })
          }
        >
          Set Nested Obj
        </button>
      </div>
    </div>
  );
}
</string></boolean>

Caractéristiques

  • Prend en charge diverses structures d'état : gère les primitives, les objets, les tableaux et les structures de données imbriquées.

  • API simple :

    • set : Mettez à jour les valeurs d'état directement ou via un rappel.
    • réinitialiser : rétablir l'état à sa valeur initiale.
    • fusionner : fusionner les mises à jour partielles dans l'état existant.
  • Type-Safe : entièrement typé à l'aide de TypeScript pour un développement fiable.

Définition

Le hook useCustomReducer est un hook React personnalisé pour gérer un état complexe. Il fournit trois méthodes principales : définir, réinitialiser et fusionner pour gérer les structures d'état primitives, imbriquées et basées sur des tableaux. Voici une description du hook et de ses méthodes :

function useCustomReducer<t extends state>(
  initialState: T
): [
  T,
  {
    set: (payload: Partial<t> | ((prevState: T) => Partial<t>)) => void;
    reset: (payload?: T) => void;
    merge: (payload: Partial<t>) => void;
  }
];
</t></t></t></t>

Définitions des méthodes

  • ensemble
    • Mise à jour l'état en remplaçant ou en mettant à jour partiellement ses propriétés.
    • Accepte soit :
    • Un objet avec de nouvelles valeurs d'état.
    • Une fonction de rappel (prevState) => Partiel pour calculer l'état suivant.

Exemple

const [state, { set }] = useCustomReducer({ count: 0 });

set((prevState) => ({ count: prevState.count + 1 }));
  • réinitialiser
    • Réinitialise l'état à l'état initial ou à une valeur spécifiée.
    • Accepte une charge utile facultative pour remplacer l'état initial.

Exemple

reset(); // Resets to initial state.

reset({ name: "John", age: 25 }); // Resets to a new state.
  • fusionner
    • Fusionne les mises à jour partielles dans l'état existant.
    • Accepte un objet avec des mises à jour d'état partielles.
    • Fonctionne uniquement pour les objets et les structures d'état imbriquées.

Exemple

merge({ city: "New York" }); // Adds or updates the 'city' field.

Exemples d'utilisation détaillés

Le hook useCustomReducer est polyvalent et peut être utilisé pour gérer différents types de structures étatiques. Voici quelques exemples pour démontrer son utilisation avec différents types d'état :

 Gestion des primitives

  • Numéro :
const initialState = 0;

const [count, { set, reset }] = useCustomReducer(initialState);
  • Utilisation :

    • Incrémentez le nombre :
    set((prevState) => prevState + 1);
    
    • Réinitialiser à l'état initial :
    reset();
    
    • Définissez une nouvelle valeur :
      set(10);
    
  • Chaîne :

const initialState = "Hello, World!";

const [message, { set, reset }] = useCustomReducer(initialState);
  • Utilisation :

    • Mettre à jour la chaîne :
    import { useReducer, useCallback, useMemo } from "react";
    
    type Primitive = boolean | string | number | Date | null | undefined;
    type NestedObject = { [key: string]: Primitive | NestedObject | NestedArray };
    type NestedArray = Array<primitive nestedobject>;
    
    type State = Primitive | NestedObject | NestedArray;
    
    type Action<t> =
      | { type: "SET"; payload: Partial<t> | ((prevState: T) => Partial<t>) }
      | { type: "RESET"; payload?: T }
      | { type: "MERGE"; payload: Partial<t> };
    
    function useCustomReducer<t extends state>(initialState: T) {
      const reducer = useCallback(
        (state: T, action: Action<t>): T => {
          switch (action.type) {
            case "SET":
              const newPayload =
                typeof action.payload === "function"
                  ? action.payload(state)
                  : action.payload;
              if (newPayload instanceof Date) {
                return newPayload as T;
              }
              if (
                typeof state === "object" &&
                !Array.isArray(state) &&
                state !== null
              ) {
                return { ...state, ...newPayload };
              }
              return newPayload as T;
            case "RESET":
              return action.payload ?? initialState;
            case "MERGE":
              if (
                typeof state === "object" &&
                !Array.isArray(state) &&
                state !== null
              ) {
                return { ...state, ...action.payload };
              }
              return action.payload as T;
            default:
              throw new Error("Invalid action type");
          }
        },
        [initialState]
      );
    
      const [state, dispatch] = useReducer(reducer, initialState);
    
      const set = useCallback(
        (payload: Partial<t> | ((prevState: T) => Partial<t>)) =>
          dispatch({ type: "SET", payload }),
        []
      );
      const reset = useCallback(
        (payload?: T) => dispatch({ type: "RESET", payload }),
        []
      );
      const merge = useCallback(
        (payload: Partial<t>) => dispatch({ type: "MERGE", payload }),
        []
      );
    
      const memoizedState = useMemo(() => state, [state]);
    
      return [memoizedState, { set, reset, merge }] as const;
    }
    
    export default useCustomReducer;
    </t></t></t></t></t></t></t></t></t></primitive>
    • Réinitialiser à l'état initial :
    import useCustomReducer from "./use-custom-reducer";
    import { faker } from "@faker-js/faker";
    import { Button } from "@/components/ui/button";
    
    export default function Use() {
      const [formValues, { set, reset, merge }] = useCustomReducer({
        name: faker.person.firstName(),
        age: faker.number.int({ min: 18, max: 99 }),
        address: {
          street: faker.location.streetAddress(),
          city: faker.location.city(),
          state: faker.location.state(),
          zip: faker.location.zipCode(),
        },
        hobbies: [faker.person.bio(), faker.person.bio(), faker.person.bio()],
      });
    
      const [bool, { set: setBool }] = useCustomReducer<boolean>(
        faker.datatype.boolean()
      );
      const [num, { set: setNum }] = useCustomReducer(faker.number.int());
      const [str, { set: setStr }] = useCustomReducer<string>(faker.lorem.word());
      const [date, { set: setDate }] = useCustomReducer(faker.date.recent());
      const [nil, { set: setNil }] = useCustomReducer(null);
      const [undef, { set: setUndef }] = useCustomReducer(undefined);
      const [arr, { set: setArr }] = useCustomReducer([
        faker.number.int(),
        faker.number.int(),
        faker.number.int(),
      ]);
      const [nestedArr, { set: setNestedArr }] = useCustomReducer([
        faker.number.int(),
        faker.lorem.word(),
        { three: faker.number.float() },
      ]);
    
      const [obj, { set: setObj }] = useCustomReducer({
        a: faker.number.int(),
        b: faker.number.int(),
        c: faker.number.int(),
      });
      const [nestedObj, { set: setNestedObj }] = useCustomReducer({
        a: faker.number.int(),
        b: faker.lorem.word(),
        c: { three: faker.number.float() },
      });
    
      return (
        <div classname="p-4 space-y-6">
          <h1 id="Use">Use</h1>
          <div classname="space-x-2 space-y-2">
            <h2 id="Form-Values">Form Values</h2>
            <p classname="text-gray-500">{JSON.stringify(formValues)}</p>
            <button onclick="{()"> set({ name: faker.person.firstName() })}>
              Set Name
            </button>
            <button onclick="{()"> set((prevState) => ({ age: prevState.age - 1 }))}
            >
              Decrement Age
            </button>
            <button onclick="{()"> set((prevState) => ({ age: prevState.age + 1 }))}
            >
              Increment Age
            </button>
            <button onclick="{()">
                set((prevState) => ({
                  address: {
                    ...prevState.address,
                    street: faker.location.streetAddress(),
                  },
                }))
              }
            >
              Set Street
            </button>
            <button onclick="{()"> reset()}>Reset</button>
            <button onclick="{()"> merge({ age: faker.number.int({ min: 18, max: 99 }) })}
            >
              Merge
            </button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="Boolean-Value">Boolean Value</h2>
            <p classname="text-gray-500">{bool.toString()}</p>
            <button onclick="{()"> setBool(faker.datatype.boolean())}>
              Set Bool
            </button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="Number-Value">Number Value</h2>
            <p classname="text-gray-500">{num.toString()}</p>
            <button onclick="{()"> setNum(faker.number.int())}>Set Num</button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="String-Value">String Value</h2>
            <p classname="text-gray-500">{str}</p>
            <button onclick="{()"> setStr(faker.lorem.word())}>Set Str</button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="Date-Value">Date Value</h2>
            <p classname="text-gray-500">{JSON.stringify(date)}</p>
            <button onclick="{()"> setDate(faker.date.recent())}>Set Date</button>
            <button onclick="{()"> setDate(new Date("2022-01-01"))}>
              Set Date to 2022
            </button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="Nil-and-Undefined">Nil and Undefined</h2>
            <p classname="text-gray-500">{String(nil)}</p>
            <button onclick="{()"> setNil(null)}>Set Nil</button>
            <p classname="text-gray-500">{String(undef)}</p>
            <button onclick="{()"> setUndef(undefined)}>Set Undef</button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="Array-Value">Array Value</h2>
            <p classname="text-gray-500">{arr.toString()}</p>
            <button onclick="{()">
                setArr([faker.number.int(), faker.number.int(), faker.number.int()])
              }
            >
              Set Arr
            </button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="Nested-Array">Nested Array</h2>
            <p classname="text-gray-500">{JSON.stringify(nestedArr)}</p>
            <button onclick="{()">
                setNestedArr([
                  faker.number.int(),
                  faker.lorem.word(),
                  { three: faker.number.float() },
                ])
              }
            >
              Set Nested Arr
            </button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="Object-Value">Object Value</h2>
            <p classname="text-gray-500">{JSON.stringify(obj)}</p>
            <button onclick="{()">
                setObj({
                  a: faker.number.int(),
                  b: faker.number.int(),
                  c: faker.number.int(),
                })
              }
            >
              Set Obj
            </button>
          </div>
          <hr classname="border-t border-gray-300">
          <div classname="space-x-2 space-y-2">
            <h2 id="Nested-Object">Nested Object</h2>
            <p classname="text-gray-500">{JSON.stringify(nestedObj)}</p>
            <button onclick="{()">
                setNestedObj({
                  a: faker.number.int(),
                  b: faker.lorem.word(),
                  c: { three: faker.number.float() },
                })
              }
            >
              Set Nested Obj
            </button>
          </div>
        </div>
      );
    }
    </string></boolean>
  • Booléen :

function useCustomReducer<t extends state>(
  initialState: T
): [
  T,
  {
    set: (payload: Partial<t> | ((prevState: T) => Partial<t>)) => void;
    reset: (payload?: T) => void;
    merge: (payload: Partial<t>) => void;
  }
];
</t></t></t></t>
  • Utilisation :

    • Basculez le booléen :
    const [state, { set }] = useCustomReducer({ count: 0 });
    
    set((prevState) => ({ count: prevState.count + 1 }));
    
    • Réinitialiser à l'état initial :
    reset(); // Resets to initial state.
    
    reset({ name: "John", age: 25 }); // Resets to a new state.
    
    • Définissez une nouvelle valeur :
    merge({ city: "New York" }); // Adds or updates the 'city' field.
    
  • Date :

const initialState = 0;

const [count, { set, reset }] = useCustomReducer(initialState);
  • Utilisation :

    • Mettre à jour la date :
    set((prevState) => prevState + 1);
    
    • Réinitialiser à l'état initial :
    reset();
    
    • Définissez une nouvelle valeur :
      set(10);
    
  • États nuls et non définis :

const initialState = "Hello, World!";

const [message, { set, reset }] = useCustomReducer(initialState);
  • Utilisation :

    • Définissez une nouvelle valeur :
    set("Hello, React!");
    
    • Réinitialiser à l'état initial :
    reset();
    
    • Définissez une nouvelle valeur :
    const initialState = false;
    
    const [isToggled, { set, reset }] = useCustomReducer(initialState);
    

Gestion des données de formulaire

  • État initial :
set((prevState) => !prevState);
  • Utilisation :

    • Définissez un nouveau nom :
    reset();
    
    • Mettre à jour l'adresse partiellement :
      set(true);
    
    • Définissez un nouveau nom :
    const initialState = new Date();
    
    const [date, { set, reset }] = useCustomReducer(initialState);
    
    • Mettre à jour la ville :
    set(new Date("2022-01-01"));
    
    • Fusionner les champs supplémentaires :
    reset();
    
    • Réinitialiser à l'état initial :
    set(new Date("2023-01-01"));
    

Gestion des tableaux

  • État initial :
const initialState: string | null = null;
const initialState: string | undefined = undefined;

const [value, { set, reset }] = useCustomReducer(initialState); // Implicitly infer the type.
const [value, { set, reset }] = useCustomReducer<string undefined>(
  initialState
); // Explicitly define the type.
</string>
  • Utilisation :

    • Ajouter un nouvel élément :
    set("New Value");
    
    • Supprimer un élément :
    reset();
    
    • Réinitialiser à l'état initial :
    set("New Value");
    
    • Définissez une nouvelle valeur :
    const initialState = {
      name: "John Doe",
      age: 30,
      address: {
        street: "123 Main St",
        city: "Sample City",
        state: "CA",
      },
    };
    
    const [formData, { set, reset, merge }] = useCustomReducer(initialState);
    
    • Fusionner des éléments supplémentaires :
    set({ name: "Jane Doe" });
    
  • État initial des tableaux imbriqués :

set((prevState) => ({
  address: {
    ...prevState.address,
    city: "New City",
  },
}));
  • Utilisation :

    • Ajouter un nouvel utilisateur :
    set({ name: "Jane Doe" });
    
    • Supprimer un utilisateur :
    merge({ address: { city: "New York" } });
    
    • Réinitialiser à l'état initial :
    merge({ phone: "123-456-7890" });
    
    • Définissez une nouvelle valeur :
    reset();
    
    • Fusionner des utilisateurs supplémentaires :
    const initialState = [1, 2, 3, 4, 5];
    
    const [numbers, { set, reset, merge }] = useCustomReducer(initialState);
    

Gestion de l'état imbriqué

  • État initial :
set((prevState) => [...prevState, 6]);
  • Utilisation :

    • Mettre à jour l'âge de l'utilisateur :
    set((prevState) => prevState.filter((item) => item !== 3));
    
    • Mettre à jour la ville :
    reset();
    
    • Réinitialiser à l'état initial :
      set([10, 20, 30]);
    
    • Définissez une nouvelle valeur :
      merge([6, 7, 8]);
    

Pourquoi utiliser useCustomReducer ?

  • Gestion d'état flexible :

    • Prend en charge diverses structures étatiques, ce qui le rend adapté à différents cas d'utilisation.
    • Gère facilement les états primitifs, imbriqués et basés sur des tableaux.
    • Fournit des méthodes pour mettre à jour, réinitialiser et fusionner les valeurs d'état.
  • API simple :

    • Fournit des méthodes intuitives pour mettre à jour, réinitialiser et fusionner des valeurs.
    • Prend en charge les mises à jour directes et les fonctions de rappel pour les changements d'état dynamiques.
    • Offre un moyen propre et déclaratif de gérer l'état dans les composants React.
  • Code du nettoyeur :

    • Réduit le code passe-partout en gérant efficacement les structures étatiques complexes.
    • Évitez les déclarations useState répétitives et gérez directement les états complexes.
    • Gérez tous les types d'état (primitif, objet, tableau, etc.) avec un seul hook.
  • Type-Safe :

    • Entièrement tapé à l'aide de TypeScript pour un développement fiable et une prévention des erreurs.
  • Mises à jour dynamiques :

    • Utilisez la méthode set avec des fonctions pour calculer dynamiquement l'état suivant.

Conclusion

Le hook useCustomReducer est un outil puissant pour gérer des structures d'état complexes dans les applications React. En combinant la flexibilité de useReducer avec une API simple pour mettre à jour l'état, ce hook simplifie la gestion de l'état et réduit le code passe-partout. Que vous ayez affaire à des valeurs primitives, des objets imbriqués ou des tableaux, le hook useCustomReducer fournit un moyen propre et déclaratif de gérer les changements d'état. Essayez-le dans votre prochain projet et découvrez facilement les avantages d'une gestion d'état polyvalente.

Ressources supplémentaires

  • Documentation React
  • Documentation TypeScript
  • Documentation Faker.js

Ce qui précède est le contenu détaillé de. pour plus d'informations, suivez d'autres articles connexes sur le site Web de PHP en chinois!

Déclaration
Le contenu de cet article est volontairement contribué par les internautes et les droits d'auteur appartiennent à l'auteur original. Ce site n'assume aucune responsabilité légale correspondante. Si vous trouvez un contenu suspecté de plagiat ou de contrefaçon, veuillez contacter admin@php.cn
Remplacer les caractères de chaîne en javascriptRemplacer les caractères de chaîne en javascriptMar 11, 2025 am 12:07 AM

Explication détaillée de la méthode de remplacement de la chaîne JavaScript et de la FAQ Cet article explorera deux façons de remplacer les caractères de chaîne dans JavaScript: le code JavaScript interne et le HTML interne pour les pages Web. Remplacer la chaîne dans le code JavaScript Le moyen le plus direct consiste à utiliser la méthode Remplace (): str = str.replace ("trouver", "remplacer"); Cette méthode remplace uniquement la première correspondance. Pour remplacer toutes les correspondances, utilisez une expression régulière et ajoutez le drapeau global G: str = str.replace (/ fi

Créez vos propres applications Web AjaxCréez vos propres applications Web AjaxMar 09, 2025 am 12:11 AM

Vous voici donc, prêt à tout savoir sur cette chose appelée Ajax. Mais qu'est-ce que c'est exactement? Le terme Ajax fait référence à un regroupement lâche de technologies utilisées pour créer un contenu Web interactif dynamique. Le terme Ajax, inventé à l'origine par Jesse J

Comment créer et publier mes propres bibliothèques JavaScript?Comment créer et publier mes propres bibliothèques JavaScript?Mar 18, 2025 pm 03:12 PM

L'article discute de la création, de la publication et du maintien des bibliothèques JavaScript, en se concentrant sur la planification, le développement, les tests, la documentation et les stratégies de promotion.

Comment optimiser le code JavaScript pour les performances dans le navigateur?Comment optimiser le code JavaScript pour les performances dans le navigateur?Mar 18, 2025 pm 03:14 PM

L'article traite des stratégies pour optimiser les performances JavaScript dans les navigateurs, en nous concentrant sur la réduction du temps d'exécution et la minimisation de l'impact sur la vitesse de chargement de la page.

Comment déboguer efficacement le code JavaScript à l'aide d'outils de développeur de navigateur?Comment déboguer efficacement le code JavaScript à l'aide d'outils de développeur de navigateur?Mar 18, 2025 pm 03:16 PM

L'article traite du débogage efficace de JavaScript à l'aide d'outils de développeur de navigateur, de se concentrer sur la définition des points d'arrêt, de l'utilisation de la console et d'analyser les performances.

Effets de la matrice jQueryEffets de la matrice jQueryMar 10, 2025 am 12:52 AM

Apportez des effets de film de matrice à votre page! Ceci est un plugin jQuery cool basé sur le célèbre film "The Matrix". Le plugin simule les effets de caractère vert classique dans le film, et sélectionnez simplement une image et le plugin le convertira en une image de style matrice remplie de caractères numériques. Venez et essayez, c'est très intéressant! Comment ça marche Le plugin charge l'image sur la toile et lit le pixel et les valeurs de couleur: data = ctx.getImagedata (x, y, settings.grainsize, settings.grainsize) .data Le plugin lit intelligemment la zone rectangulaire de l'image et utilise jQuery pour calculer la couleur moyenne de chaque zone. Ensuite, utilisez

Comment construire un simple curseur jQueryComment construire un simple curseur jQueryMar 11, 2025 am 12:19 AM

Cet article vous guidera pour créer un carrousel d'image simple à l'aide de la bibliothèque JQuery. Nous utiliserons la bibliothèque BXSLider, qui est construite sur jQuery et offre de nombreuses options de configuration pour configurer le carrousel. De nos jours, Picture Carrousel est devenue une fonctionnalité incontournable sur le site Web - une image vaut mieux que mille mots! Après avoir décidé d'utiliser le carrousel d'image, la question suivante est de savoir comment la créer. Tout d'abord, vous devez collecter des images de haute qualité et haute résolution. Ensuite, vous devez créer un carrousel d'image en utilisant HTML et un code JavaScript. Il existe de nombreuses bibliothèques sur le Web qui peuvent vous aider à créer des carrousels de différentes manières. Nous utiliserons la bibliothèque BXSLider open source. La bibliothèque Bxslider prend en charge la conception réactive, de sorte que le carrousel construit avec cette bibliothèque peut être adapté à n'importe quel

Comment télécharger et télécharger des fichiers CSV avec AngularComment télécharger et télécharger des fichiers CSV avec AngularMar 10, 2025 am 01:01 AM

Les ensembles de données sont extrêmement essentiels pour créer des modèles d'API et divers processus métier. C'est pourquoi l'importation et l'exportation de CSV sont une fonctionnalité souvent nécessaire. Dans ce tutoriel, vous apprendrez à télécharger et à importer un fichier CSV dans un

See all articles

Outils d'IA chauds

Undresser.AI Undress

Undresser.AI Undress

Application basée sur l'IA pour créer des photos de nu réalistes

AI Clothes Remover

AI Clothes Remover

Outil d'IA en ligne pour supprimer les vêtements des photos.

Undress AI Tool

Undress AI Tool

Images de déshabillage gratuites

Clothoff.io

Clothoff.io

Dissolvant de vêtements AI

AI Hentai Generator

AI Hentai Generator

Générez AI Hentai gratuitement.

Article chaud

R.E.P.O. Crystals d'énergie expliqués et ce qu'ils font (cristal jaune)
3 Il y a quelques semainesBy尊渡假赌尊渡假赌尊渡假赌
R.E.P.O. Meilleurs paramètres graphiques
3 Il y a quelques semainesBy尊渡假赌尊渡假赌尊渡假赌
R.E.P.O. Comment réparer l'audio si vous n'entendez personne
3 Il y a quelques semainesBy尊渡假赌尊渡假赌尊渡假赌

Outils chauds

SublimeText3 version Mac

SublimeText3 version Mac

Logiciel d'édition de code au niveau de Dieu (SublimeText3)

Dreamweaver Mac

Dreamweaver Mac

Outils de développement Web visuel

PhpStorm version Mac

PhpStorm version Mac

Le dernier (2018.2.1) outil de développement intégré PHP professionnel

ZendStudio 13.5.1 Mac

ZendStudio 13.5.1 Mac

Puissant environnement de développement intégré PHP

SublimeText3 version chinoise

SublimeText3 version chinoise

Version chinoise, très simple à utiliser