【问题标题】:How to remove an element from an array dynamically? React.js如何动态地从数组中删除元素?反应.js
【发布时间】:2020-11-11 19:28:43
【问题描述】:

有两个组件,我想用useContext钩子实现一个元素数组,但是当按钮被点击的时候,元素并没有被移除,反而多了个。告诉我这里出了什么问题。我将不胜感激!

第一个组件:

import React from 'react';
import CartItem from './CartItem';
import Context from '../Context'; 

function Cart() {
    let sum = 0;
    let arrPrice = [];
    let [products, setProducts] = React.useState([]);
    let loacalProsucts = JSON.parse(localStorage.getItem('products'));

    if(loacalProsucts === null) {
        return(
            <div className="EmptyCart">
                <h1>Cart is empty</h1>
            </div>
        )
    } else {
        {loacalProsucts.map(item => products.push(item))}
        {loacalProsucts.map(item => arrPrice.push(JSON.parse(item.total)))}
    }

    for(let i in arrPrice) {
        sum += arrPrice[i];
    }

    function removeItem(id) {
        setProducts(
            products.filter(item => item.id !== id)
        )
    }

    return(
        <Context.Provider value={{removeItem}}>
            <div className="Cart">
                <h1>Your purchases:</h1>
                <CartItem products = {products} />
                <h1>Total: {sum}$</h1>
            </div>
        </Context.Provider>
    )
}

第二部分:

import React, { useContext } from 'react';
import Context from '../Context';

function CartList({products}) {
    const {removeItem} = useContext(Context);
    return(
        <div className="CartList">
            <img src={products.image} />
            <h2>{products.name}</h2>
            <h3 className="CartInfo">{products.kg}kg.</h3>
            <h2 className="CartInfo">{products.total}$</h2>
            <button className="CartInfo" onClick={() => removeItem(products.id)}>&times;</button>
        </div>
    );
}

export default CartList;

带有上下文的组件:

import React from 'react';

const Context = React.createContext();

export default Context;

【问题讨论】:

  • 渲染循环中的所有代码,例如products.push(item),每次组件渲染时都会运行。这就是 React 钩子的用途。

标签: javascript arrays reactjs react-hooks


【解决方案1】:

添加到上面的评论^^

在渲染循环中(即在钩子之外)包含初始化表达式几乎总是一个错误。您还需要避免改变本地状态,这就是 useState 返回 setter 的原因。

完全未经测试:

function Cart() {
  let [sum, setSum] = React.useState();
  const loacalProsucts = useMemo(() => JSON.parse(localStorage.getItem('products')));
  // Init products with local products if they exist
  let [products, setProducts] = React.useState(loacalProsucts || []);

  useEffect(() => {
    // This is actually derived state so the whole thing
    // could be replaced with
    // const sum = products.reduce((a, c) => a + c?.total, 0);
    setSum(products.reduce((a, c) => a + c?.total, 0));
  }, [products]);

  function removeItem(id) {
    setProducts(
      products.filter(item => item.id !== id)
    )
  }

...

【讨论】:

    猜你喜欢
    • 2021-04-09
    • 2021-08-30
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2022-01-23
    • 2020-05-23
    • 2021-09-15
    相关资源
    最近更新 更多