You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React表格复选框未按预期增删数组元素 点击两次才生效问题

问题根源
  • React的状态更新为异步批量执行,事件回调中读取到的newdatatoshow永远是本次渲染的旧值,你连续两次调用setnewdatatoshow的逻辑本身也存在冲突,先添加再判断删除的操作完全不符合需求
  • 点击事件绑定在了span标签上,触发事件的target可能是span而非input,无法正确获取复选框的勾选状态
  • 没有给input的checked属性绑定对应值,复选框的显示状态和数组存储的id没有关联,二者状态不同步
  • 你在setnewdatatoshow执行后立即打印状态,拿到的是更新前的旧值,所以会出现第一次点击打印空数组的错觉
修正方案

将事件绑定到input的onChange事件上,使用函数式更新保证拿到最新的状态,同时绑定checked属性实现状态同步:

import "./styles.css";
import { useState, useEffect } from "react";

export default function App() {
  const Defaultdata = [
    {
      date_listed: "4 hours ago",
      id: "7857699961",
      delivery_time_frame: "2021-10-25 - 2021-11-14",
      distance: "22.8 km",
      time_stamp: "2021-10-25 16:36:54",
      watched: "yes"
    },
    {
      date_listed: "3 days ago",
      id: "8358962006",
      delivery_time_frame: "2021-10-18 - 2021-10-24",
      distance: "4.3 km",
      time_stamp: "2021-10-22 16:54:12"
    },
    {
      date_listed: "4 hours ago",
      id: "8146462294",
      delivery_time_frame: "2021-10-25",
      distance: "4.3 km",
      time_stamp: "2021-10-25 16:12:32"
    }
  ];

  const [newdatatoshow, setnewdatatoshow] = useState([]);
  // 监听数组变化打印最新值
  useEffect(() => {
    console.log(newdatatoshow);
  }, [newdatatoshow])

  return (
    <div className="App">
      <h1>Hello CodeSandbox</h1>
      <h2>Start editing to see some magic happen!</h2>

      <table>
        <thead>
          <th></th>
          <th>Item 1</th>
          <th>Item 2</th>
          <th>Item 3</th>
          <th>Item 4</th>
        </thead>
        <tbody>
          {Defaultdata.map((item, index) => {
            return (
              <tr key={index}>
                <td>
                  <input 
                    type="checkbox" 
                    checked={newdatatoshow.includes(item.id)}
                    onChange={(e) => {
                      if (e.target.checked) {
                        // 函数式更新取最新的前态
                        setnewdatatoshow(prev => [...prev, item.id])
                      } else {
                        setnewdatatoshow(prev => prev.filter(n => n !== item.id))
                      }
                    }}
                  />
                </td>
                <td>{item.id}</td>
                <td>{item.distance}</td>
                <td>{item.date_listed}</td>
              </tr>
            );
          })}
        </tbody>
      </table>
    </div>
  );
}

内容的提问来源于stack exchange,提问作者s life

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.28 16:54:06