suchen
HeimWeb-Frontendjs-TutorialuseCustomReducer Hook: Ein vielseitiges Statusverwaltungstool

useCustomReducer Hook: A Versatile State Management Tool

Einführung

Die Zustandsverwaltung in React kann schwierig sein, insbesondere wenn es um komplexe oder verschachtelte Zustandsstrukturen geht. Um dies zu vereinfachen, kombiniert der useCustomReducer-Hook die Leistungsfähigkeit von useReducer mit einer flexiblen API zum Aktualisieren des Status auf saubere, deklarative Weise. Dieser Hook unterstützt primitive, verschachtelte und Array-Zustände und eignet sich daher für eine Vielzahl von Anwendungsfällen.

In diesem Artikel untersuchen wir den useCustomReducer-Hook und seine Kernmethoden zum Verwalten des Status in React-Anwendungen. Wir behandeln die Definition des Hooks, seine Methodensignaturen und detaillierte Anwendungsbeispiele für verschiedene Arten von Zustandsstrukturen. Am Ende verfügen Sie über ein solides Verständnis dafür, wie Sie den useCustomReducer-Hook verwenden, um komplexe Zustände in Ihren React-Komponenten zu verarbeiten.

 Inhaltsverzeichnis

  • Einführung
  • Inhaltsverzeichnis
  • Hooks-Übersicht
  • Beispiel für eine Reaktionskomponente
  • Funktionen
  • Definition
    • Methodendefinitionen
  • Detaillierte Anwendungsbeispiele
    • Primitive verwalten
    • Formulardaten verwalten
    • Arrays verwalten
    • Verschachtelungsstatus verwalten
  • Warum useCustomReducer verwenden?
  • Fazit
  • Zusätzliche Ressourcen

Hooks-Übersicht

Der useCustomReducer-Hook ist ein benutzerdefinierter React-Hook, der eine einfache und flexible Möglichkeit bietet, komplexe Zustandsstrukturen zu verwalten. Es kombiniert die Vorteile von useReducer mit einer sauberen API zum Aktualisieren von Statuswerten. Dieser Hook ist für die Verarbeitung verschiedener Zustandstypen konzipiert, darunter Grundwerte, Objekte, Arrays und verschachtelte Datenstrukturen.

Hier ist eine Übersicht über den useCustomReducer-Hook:

  • Kernmethoden:

    • set: Zustandswerte direkt oder über eine Callback-Funktion aktualisieren.
    • Zurücksetzen: Zustand auf seinen Anfangswert zurücksetzen.
    • merge: Teilaktualisierungen in den bestehenden Zustand einbinden.
  • Zustandsstrukturen: - Unterstützt primitive Werte (z. B. Zahlen, Zeichenfolgen, Boolesche Werte). - Verarbeitet objektbasierte Zustandsstrukturen (z. B. Formulardaten, Benutzerprofile). - Verwaltet Array-basierte Zustandsstrukturen (z. B. Listen, Sammlungen).

  • Typsicher: - Vollständig typisiert mit TypeScript für zuverlässige Entwicklung und Fehlervermeidung.

  • Einfache API: – Bietet intuitive Methoden zum Aktualisieren, Zurücksetzen und Zusammenführen von Statuswerten. - Unterstützt direkte Aktualisierungen und Rückruffunktionen für dynamische Statusänderungen.

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>

Der useCustomReducer-Hook wird mithilfe des useReducer-Hooks von React implementiert. Es definiert eine benutzerdefinierte Reduzierfunktion, die verschiedene Arten von Aktionen zum Aktualisieren, Zurücksetzen oder Zusammenführen von Statuswerten verarbeitet. Der Hook bietet drei Kernmethoden zum Festlegen, Zurücksetzen und Zusammenführen, um mit dem Status zu interagieren. Die Set-Methode kann entweder ein Objekt mit neuen Statuswerten oder eine Rückruffunktion akzeptieren, um den nächsten Status zu berechnen. Die Reset-Methode setzt den Zustand auf seinen Anfangswert zurück, während die Merge-Methode Teilaktualisierungen in den bestehenden Zustand einfügt.

Beispiel für eine Reaktionskomponente

Hier ist ein Beispiel für die Verwendung des useCustomReducer-Hooks in einer React-Komponente, um einen einfachen Zählerstatus zu verwalten:

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>

Merkmale

  • Unterstützt verschiedene Zustandsstrukturen: Behandelt Grundelemente, Objekte, Arrays und verschachtelte Datenstrukturen.

  • Einfache API:

    • set: Zustandswerte direkt oder über einen Rückruf aktualisieren.
    • Zurücksetzen: Zustand auf seinen Anfangswert zurücksetzen.
    • merge: Teilaktualisierungen in den bestehenden Zustand einbinden.
  • Typsicher: Vollständig typisiert mit TypeScript für zuverlässige Entwicklung.

Definition

Der useCustomReducer-Hook ist ein benutzerdefinierter React-Hook zur Verwaltung komplexer Zustände. Es bietet drei Kernmethoden zum Festlegen, Zurücksetzen und Zusammenführen, um primitive, verschachtelte und arraybasierte Zustandsstrukturen zu verarbeiten. Hier ist eine Aufschlüsselung des Hooks und seiner Methoden:

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>

Methodendefinitionen

  • Satz
    • Aktualisiert den Status durch Ersetzen oder teilweises Aktualisieren seiner Eigenschaften.
    • Akzeptiert entweder:
    • Ein Objekt mit neuen Zustandswerten.
    • Eine Rückruffunktion (prevState) => Teilweise zur Berechnung des nächsten Zustands.

Beispiel

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

set((prevState) => ({ count: prevState.count + 1 }));
  • zurücksetzen
    • Setzt den Zustand auf den Anfangszustand oder einen angegebenen Wert zurück.
    • Akzeptiert eine optionale Nutzlast, um den Anfangszustand zu ersetzen.

Beispiel

reset(); // Resets to initial state.

reset({ name: "John", age: 25 }); // Resets to a new state.
  • verschmelzen
    • Führt Teilaktualisierungen in den bestehenden Zustand ein.
    • Akzeptiert ein Objekt mit teilweisen Statusaktualisierungen.
    • Funktioniert nur für Objekte und verschachtelte Zustandsstrukturen.

Beispiel

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

Detaillierte Anwendungsbeispiele

Der useCustomReducer-Hook ist vielseitig und kann zur Verwaltung verschiedener Arten von Zustandsstrukturen verwendet werden. Hier sind einige Beispiele, um die Verwendung mit verschiedenen Zustandstypen zu veranschaulichen:

 Primitive verwalten

  • Nummer:
const initialState = 0;

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

    • Erhöhen Sie die Anzahl:
    set((prevState) => prevState + 1);
    
    • Zurücksetzen auf den Ausgangszustand:
    reset();
    
    • Neuen Wert festlegen:
      set(10);
    
  • Zeichenfolge:

const initialState = "Hello, World!";

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

    • Aktualisieren Sie die Zeichenfolge:
    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>
    • Zurücksetzen auf den Ausgangszustand:
    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>
  • Boolescher Wert:

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>
  • Verwendung:

    • Booleschen Wert umschalten:
    const [state, { set }] = useCustomReducer({ count: 0 });
    
    set((prevState) => ({ count: prevState.count + 1 }));
    
    • Zurücksetzen auf den Ausgangszustand:
    reset(); // Resets to initial state.
    
    reset({ name: "John", age: 25 }); // Resets to a new state.
    
    • Neuen Wert festlegen:
    merge({ city: "New York" }); // Adds or updates the 'city' field.
    
  • Datum:

const initialState = 0;

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

    • Datum aktualisieren:
    set((prevState) => prevState + 1);
    
    • Zurücksetzen auf den Ausgangszustand:
    reset();
    
    • Neuen Wert festlegen:
      set(10);
    
  • Null- und undefinierte Zustände:

const initialState = "Hello, World!";

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

    • Neuen Wert festlegen:
    set("Hello, React!");
    
    • Zurücksetzen auf den Ausgangszustand:
    reset();
    
    • Neuen Wert festlegen:
    const initialState = false;
    
    const [isToggled, { set, reset }] = useCustomReducer(initialState);
    

Formulardaten verwalten

  • Ausgangszustand:
set((prevState) => !prevState);
  • Verwendung:

    • Neuen Namen festlegen:
    reset();
    
    • Adresse teilweise aktualisieren:
      set(true);
    
    • Neuen Namen festlegen:
    const initialState = new Date();
    
    const [date, { set, reset }] = useCustomReducer(initialState);
    
    • Aktualisieren Sie die Stadt:
    set(new Date("2022-01-01"));
    
    • Zusätzliche Felder zusammenführen:
    reset();
    
    • Zurücksetzen auf den Ausgangszustand:
    set(new Date("2023-01-01"));
    

Arrays verwalten

  • Ausgangszustand:
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>
  • Verwendung:

    • Neues Element hinzufügen:
    set("New Value");
    
    • Ein Element entfernen:
    reset();
    
    • Zurücksetzen auf den Ausgangszustand:
    set("New Value");
    
    • Neuen Wert festlegen:
    const initialState = {
      name: "John Doe",
      age: 30,
      address: {
        street: "123 Main St",
        city: "Sample City",
        state: "CA",
      },
    };
    
    const [formData, { set, reset, merge }] = useCustomReducer(initialState);
    
    • Zusätzliche Elemente zusammenführen:
    set({ name: "Jane Doe" });
    
  • Anfangszustand für verschachtelte Arrays:

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

    • Neuen Benutzer hinzufügen:
    set({ name: "Jane Doe" });
    
    • Einen Benutzer entfernen:
    merge({ address: { city: "New York" } });
    
    • Zurücksetzen auf den Ausgangszustand:
    merge({ phone: "123-456-7890" });
    
    • Neuen Wert festlegen:
    reset();
    
    • Zusätzliche Benutzer zusammenführen:
    const initialState = [1, 2, 3, 4, 5];
    
    const [numbers, { set, reset, merge }] = useCustomReducer(initialState);
    

Verwalten des verschachtelten Zustands

  • Ausgangszustand:
set((prevState) => [...prevState, 6]);
  • Verwendung:

    • Alter des Benutzers aktualisieren:
    set((prevState) => prevState.filter((item) => item !== 3));
    
    • Aktualisieren Sie die Stadt:
    reset();
    
    • Zurücksetzen auf den Ausgangszustand:
      set([10, 20, 30]);
    
    • Neuen Wert festlegen:
      merge([6, 7, 8]);
    

Warum useCustomReducer verwenden?

  • Flexibles Zustandsmanagement:

    • Unterstützt verschiedene Zustandsstrukturen und eignet sich daher für verschiedene Anwendungsfälle.
    • Verarbeitet problemlos primitive, verschachtelte und Array-basierte Zustände.
    • Stellt Methoden zum Aktualisieren, Zurücksetzen und Zusammenführen von Statuswerten bereit.
  • Einfache API:

    • Bietet intuitive Methoden zum Aktualisieren, Zurücksetzen und Zusammenführen von Werten.
    • Unterstützt direkte Aktualisierungen und Rückruffunktionen für dynamische Statusänderungen.
    • Bietet eine saubere und deklarative Möglichkeit, den Status in React-Komponenten zu verwalten.
  • Cleaner-Code:

    • Reduziert den Boilerplate-Code durch effiziente Handhabung komplexer Zustandsstrukturen.
    • Vermeiden Sie sich wiederholende useState-Deklarationen und verarbeiten Sie komplexe Zustände direkt.
    • Verwalten Sie alle Zustandstypen (primitiv, Objekt, Array usw.) mit einem Hook.
  • Typsicher:

    • Vollständig typisiert mit TypeScript für zuverlässige Entwicklung und Fehlervermeidung.
  • Dynamische Updates:

    • Verwenden Sie die Set-Methode mit Funktionen, um den nächsten Zustand dynamisch zu berechnen.

Abschluss

Der useCustomReducer-Hook ist ein leistungsstarkes Tool zum Verwalten komplexer Zustandsstrukturen in React-Anwendungen. Durch die Kombination der Flexibilität von useReducer mit einer einfachen API zum Aktualisieren des Status vereinfacht dieser Hook die Statusverwaltung und reduziert den Boilerplate-Code. Unabhängig davon, ob Sie mit primitiven Werten, verschachtelten Objekten oder Arrays arbeiten, bietet der useCustomReducer-Hook eine saubere und deklarative Möglichkeit, Zustandsänderungen zu verarbeiten. Probieren Sie es bei Ihrem nächsten Projekt aus und erleben Sie ganz einfach die Vorteile einer vielseitigen Zustandsverwaltung.

Zusätzliche Ressourcen

  • React Documentation
  • TypeScript-Dokumentation
  • Faker.js-Dokumentation

Das obige ist der detaillierte Inhalt vonuseCustomReducer Hook: Ein vielseitiges Statusverwaltungstool. Für weitere Informationen folgen Sie bitte anderen verwandten Artikeln auf der PHP chinesischen Website!

Stellungnahme
Der Inhalt dieses Artikels wird freiwillig von Internetnutzern beigesteuert und das Urheberrecht liegt beim ursprünglichen Autor. Diese Website übernimmt keine entsprechende rechtliche Verantwortung. Wenn Sie Inhalte finden, bei denen der Verdacht eines Plagiats oder einer Rechtsverletzung besteht, wenden Sie sich bitte an admin@php.cn
Python vs. JavaScript: Auswählen des richtigen Tools für den JobPython vs. JavaScript: Auswählen des richtigen Tools für den JobMay 08, 2025 am 12:10 AM

Ob die Auswahl von Python oder JavaScript vom Projekttyp abhängt: 1) Wählen Sie Python für Datenwissenschafts- und Automatisierungsaufgaben aus; 2) Wählen Sie JavaScript für die Entwicklung von Front-End- und Full-Stack-Entwicklung. Python ist für seine leistungsstarke Bibliothek in der Datenverarbeitung und -automatisierung bevorzugt, während JavaScript für seine Vorteile in Bezug auf Webinteraktion und Full-Stack-Entwicklung unverzichtbar ist.

Python und JavaScript: Verständnis der Stärken der einzelnenPython und JavaScript: Verständnis der Stärken der einzelnenMay 06, 2025 am 12:15 AM

Python und JavaScript haben jeweils ihre eigenen Vorteile, und die Wahl hängt von den Projektbedürfnissen und persönlichen Vorlieben ab. 1. Python ist leicht zu erlernen, mit prägnanter Syntax, die für Datenwissenschaft und Back-End-Entwicklung geeignet ist, aber eine langsame Ausführungsgeschwindigkeit hat. 2. JavaScript ist überall in der Front-End-Entwicklung und verfügt über starke asynchrone Programmierfunktionen. Node.js macht es für die Entwicklung der Vollstapel geeignet, die Syntax kann jedoch komplex und fehleranfällig sein.

JavaScripts Kern: Ist es auf C oder C aufgebaut?JavaScripts Kern: Ist es auf C oder C aufgebaut?May 05, 2025 am 12:07 AM

JavaScriptisnotbuiltoncorc; Es ist angehört, dass sich JavaScriptWasdedeSthatrunsonGineoFtencninc.

JavaScript-Anwendungen: Von Front-End bis Back-EndJavaScript-Anwendungen: Von Front-End bis Back-EndMay 04, 2025 am 12:12 AM

JavaScript kann für die Entwicklung von Front-End- und Back-End-Entwicklung verwendet werden. Das Front-End verbessert die Benutzererfahrung durch DOM-Operationen, und die Back-End-Serveraufgaben über node.js. 1. Beispiel für Front-End: Ändern Sie den Inhalt des Webseitentextes. 2. Backend Beispiel: Erstellen Sie einen Node.js -Server.

Python vs. JavaScript: Welche Sprache sollten Sie lernen?Python vs. JavaScript: Welche Sprache sollten Sie lernen?May 03, 2025 am 12:10 AM

Die Auswahl von Python oder JavaScript sollte auf Karriereentwicklung, Lernkurve und Ökosystem beruhen: 1) Karriereentwicklung: Python ist für die Entwicklung von Datenwissenschaften und Back-End-Entwicklung geeignet, während JavaScript für die Entwicklung von Front-End- und Full-Stack-Entwicklung geeignet ist. 2) Lernkurve: Die Python -Syntax ist prägnant und für Anfänger geeignet; Die JavaScript -Syntax ist flexibel. 3) Ökosystem: Python hat reichhaltige wissenschaftliche Computerbibliotheken und JavaScript hat ein leistungsstarkes Front-End-Framework.

JavaScript -Frameworks: Stromversorgung moderner WebentwicklungJavaScript -Frameworks: Stromversorgung moderner WebentwicklungMay 02, 2025 am 12:04 AM

Die Kraft des JavaScript -Frameworks liegt in der Vereinfachung der Entwicklung, der Verbesserung der Benutzererfahrung und der Anwendungsleistung. Betrachten Sie bei der Auswahl eines Frameworks: 1. Projektgröße und Komplexität, 2. Teamerfahrung, 3. Ökosystem und Community -Unterstützung.

Die Beziehung zwischen JavaScript, C und BrowsernDie Beziehung zwischen JavaScript, C und BrowsernMay 01, 2025 am 12:06 AM

Einführung Ich weiß, dass Sie es vielleicht seltsam finden. Was genau muss JavaScript, C und Browser tun? Sie scheinen nicht miteinander verbunden zu sein, aber tatsächlich spielen sie eine sehr wichtige Rolle in der modernen Webentwicklung. Heute werden wir die enge Verbindung zwischen diesen drei diskutieren. In diesem Artikel erfahren Sie, wie JavaScript im Browser ausgeführt wird, die Rolle von C in der Browser -Engine und wie sie zusammenarbeiten, um das Rendern und die Interaktion von Webseiten voranzutreiben. Wir alle kennen die Beziehung zwischen JavaScript und Browser. JavaScript ist die Kernsprache der Front-End-Entwicklung. Es läuft direkt im Browser und macht Webseiten lebhaft und interessant. Haben Sie sich jemals gefragt, warum Javascr

Node.js Streams mit TypeScriptNode.js Streams mit TypeScriptApr 30, 2025 am 08:22 AM

Node.js zeichnet sich bei effizienten E/A aus, vor allem bei Streams. Streams verarbeiten Daten inkrementell und vermeiden Speicherüberladung-ideal für große Dateien, Netzwerkaufgaben und Echtzeitanwendungen. Die Kombination von Streams mit der TypeScript -Sicherheit erzeugt eine POWE

See all articles

Heiße KI -Werkzeuge

Undresser.AI Undress

Undresser.AI Undress

KI-gestützte App zum Erstellen realistischer Aktfotos

AI Clothes Remover

AI Clothes Remover

Online-KI-Tool zum Entfernen von Kleidung aus Fotos.

Undress AI Tool

Undress AI Tool

Ausziehbilder kostenlos

Clothoff.io

Clothoff.io

KI-Kleiderentferner

Video Face Swap

Video Face Swap

Tauschen Sie Gesichter in jedem Video mühelos mit unserem völlig kostenlosen KI-Gesichtstausch-Tool aus!

Heiße Werkzeuge

Dreamweaver CS6

Dreamweaver CS6

Visuelle Webentwicklungstools

SAP NetWeaver Server-Adapter für Eclipse

SAP NetWeaver Server-Adapter für Eclipse

Integrieren Sie Eclipse mit dem SAP NetWeaver-Anwendungsserver.

mPDF

mPDF

mPDF ist eine PHP-Bibliothek, die PDF-Dateien aus UTF-8-codiertem HTML generieren kann. Der ursprüngliche Autor, Ian Back, hat mPDF geschrieben, um PDF-Dateien „on the fly“ von seiner Website auszugeben und verschiedene Sprachen zu verarbeiten. Es ist langsamer und erzeugt bei der Verwendung von Unicode-Schriftarten größere Dateien als Originalskripte wie HTML2FPDF, unterstützt aber CSS-Stile usw. und verfügt über viele Verbesserungen. Unterstützt fast alle Sprachen, einschließlich RTL (Arabisch und Hebräisch) und CJK (Chinesisch, Japanisch und Koreanisch). Unterstützt verschachtelte Elemente auf Blockebene (wie P, DIV),

Notepad++7.3.1

Notepad++7.3.1

Einfach zu bedienender und kostenloser Code-Editor

Senden Sie Studio 13.0.1

Senden Sie Studio 13.0.1

Leistungsstarke integrierte PHP-Entwicklungsumgebung