如何处理具有多个值的单个名称输入的输入表单?

how to handle input form with single name input that has many value?

我有一个 table,其中 table 有很多行数据。 enter image description here

my table 具有可以添加多行以处理多个输入的功能。到目前为止,这个在我的 table 中添加多行的功能是有效的。当我单击按钮生成多个空行时。 这是我之前使用的示例代码。此代码仅记录最后的输入。

const [newInputRows, setNewInputRows] = useState([])
const handleChangeNewRows = (event) => {
    setNewRows({...newInputRows, [event.target.name] : event.target.value})
    console.log(newInputRows)
  }

return 的以下部分。这是我生成新空行的代码::

const newRows = [0, 1, 2, 3, 4]
        <tbody>
              {
                insertRows && newRows.map(rows =>
                  <tr key={rows} id={rows}>
                    <td style={setStyle("20px")}></td>
                    {
                      _header.map((column,idc) => column === '_id' ? null : <td key={idc} className="input"><InputRows type="text" name={column} onChange={handleChangeNewRows}/></td>)
                    }
                  </tr>
                 )
               }
        </tbody>

如您所见,所有行都有多个具有相同(单个)名称的输入。我的问题是如何在单个输入名称中处理具有多个值的表单输入。因为此表单将发送到数据库有 2 个字段 countryCode 和 Country name 的后端。 我想让这个表单发送到后端成为一个对象数组,如下所示:

[
{countryCode: "A", countryName: "countryA"},
{countryCode: "B", countryName: "countryB"},
{countryCode: "C", countryName: "countryC"}
]

如何在 reactjs 中处理这个问题?

输出就是你想要的

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

const App = () => {
  const [list, setList] = useState([]);
  const handleClick = () => {
    list.splice(0, list.length);
    const inputs = document.getElementsByTagName("input");
    for (var i = 0; i < inputs.length; i++) {
      if (inputs[i].name === "countryName") {
        list.push({
          countryCode: inputs[i - 1].value,
          countryName: inputs[i].value
        });
        setList(list);
      }
    }
    console.log("list: ", JSON.stringify(list));
  };
  return (
    <>
      <table>
        <tr>
          <td>
            <input name="countryCode" />
          </td>
          <td>
            <input name="countryName" />
          </td>
        </tr>
        <tr>
          <td>
            <input name="countryCode" />
          </td>
          <td>
            <input name="countryName" />
          </td>
        </tr>
        <tr>
          <td>
            <input name="countryCode" />
          </td>
          <td>
            <input name="countryName" />
          </td>
        </tr>
      </table>
      <button onClick={handleClick}>click</button>
    </>
  );
};
export default App;

我看到的一个问题是您如何处理更新行数据,您正在将状态不变性从数组更改为对象,并且您无法唯一标识要更新的数据行。

  1. 我建议首先创建一个回调以向每一行新数据元素添加一个 id

    import { v4 as uuidV4 } from "uuid";
    
    ...
    
    const [rowData, setRowData] = useState([]);
    
    const addRow = () =>
      setRowData((rowData) =>
        rowData.concat({
          id: uuidV4(),
          countryCode: "",
          countryName: ""
        })
      );
    
  2. 使用 curried 更改处理程序在范围内关闭行 id,并使用功能状态更新浅复制先前的状态。

    const changeHandler = (rowId) => (e) => {
      const { name, value } = e.target;
      setRowData((rowData) =>
        rowData.map((data) =>
          data.id === rowId
            ? {
                ...data,
                [name]: value
              }
            : data
        )
      );
    };
    
  3. 映射行数据并附加更改处理程序。

    {rowData.map((data) => (
      <tr key={data.id}>
        <td>
          <input
            name="countryCode"
            value={data.countryCode}
            onChange={changeHandler(data.id)}
          />
        </td>
        <td>
          <input
            name="countryName"
            value={data.countryName}
            onChange={changeHandler(data.id)}
          />
        </td>
      </tr>
    ))}
    

演示

[
  {countryCode: "A", countryName: "countryA"},
  {countryCode: "B", countryName: "countryB"},
  {countryCode: "C", countryName: "countryC"}
]