# React技巧之在state数组中添加元素

原文链接:https://bobbyhadz.com/blog/react-push-to-state-array (opens new window)

作者:Borislav Hadzhiev (opens new window)

正文从这开始~

# 总览

在React中使用扩展语法,将元素添加到state数组中。比如说,setNames(current => [...current, 'Carl']) 。扩展语法会解包state数组中现存的元素,到一个新数组中。我们可以在其中添加其他元素。

import {useState} from 'react';

export default function App() {
  const [names, setNames] = useState(['Alice', 'Bob']);

  const handleClick = () => {
    // 👇️ push to end of state array
    setNames(current => [...current, 'Carl']);

    // 👇️ spread an array into the state array
    // setNames(current => [...current, ...['Carl', 'Delilah']]);

    // 👇️ push to beginning of state array
    // setNames(current => ['Zoey', ...current]);
  };

  return (
    <div>
      <div>
        <button onClick={handleClick}>Push to state array</button>
      </div>

      {names.map((element, index) => {
        return (
          <div key={index}>
            <h2>{element}</h2>
          </div>
        );
      })}
    </div>
  );
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32

push-to-state-array.png

# 添加元素

这里我们使用useState钩子来管理state数组。注意,我们给setState传递了一个函数,因为函数会保证以当前(最新的)状态调用。

setNames(current => [...current, 'Carl']);
1

当使用前一个状态计算下一个状态时,向setState传递一个函数。

否则,如果我们所访问的state数组不代表最新的值,我们可能会得到一些奇怪的竞态条件。

我们使用扩展运算符语法,来将已有数组中的元素解包到新数组中。

const arr = ['Alice', 'Bob'];

const arr2 = [...arr, 'Carl'];

console.log(arr2); // 👉️ ['Alice', 'Bob', 'Carl']
1
2
3
4
5

上面的例子创建了一个原始数组的浅复制。在React中,不允许修改原始state数组,因此我们不能直接使用push()方法。

# 添加对象

请注意,这种方法也可以用来将一个对象推送到一个state数组。

import {useState} from 'react';

export default function App() {
  const initialState = [
    {id: 1, name: 'Alice'},
    {id: 2, name: 'Bob'},
  ];
  const [employees, setEmployees] = useState(initialState);

  const handleClick = () => {
    // 👇️ push object to end of state array
    setEmployees(current => [...current, {id: 3, name: 'Carl'}]);

    // 👇️ spread an array of objects into the state array
    // setEmployees(current => [
    //   ...current,
    //   ...[
    //     {id: 3, name: 'Carl'},
    //     {id: 4, name: 'Delilah'},
    //   ],
    // ]);

    // 👇️ push object to beginning of state array
    // setEmployees(current => [{id: 3, name: 'Zoey'}, ...current]);
  };

  return (
    <div>
      <div>
        <button onClick={handleClick}>Push to state array</button>
      </div>

      {employees.map((element, index) => {
        return (
          <div key={index}>
            <h2>{element.name}</h2>
          </div>
        );
      })}
    </div>
  );
}
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42

同样的方法可以用来将一个对象推送到一个state数组。我们只需将state数组中的元素解包到一个新数组中,并添加指定的对象即可。