3

我正在使用 useSelector() 来获取状态,当我对局部状态变量应用一些过滤器时,我的全局状态正在发生变化。不知道为什么。下面是代码。

const filterVacations = (employees, status) => {
    if(status === 'Approved') {
        employees.forEach(item => {
            item.vacations = item.vacations.filter(vac => vac.approved === true);

        });
    }
    else if(status === 'Unapproved') {
        employees.forEach(item => {
            item.vacations = item.vacations.filter(vac => vac.approved === false);

    });

    }
    return employees.filter(item => item.vacations.length > 0);
  }

并调用此函数如下:

const Vacations = () => {
    const state = useSelector((state:State) => state);
    const view = state.view;
    const filter = state.filter;
    const employees = state.employees;

    employees = filterVacations(employees, filter); 

    return (
      <>
      //some component...
      </>);

  }

为什么状态在这里发生变异?

4

2 回答 2

1

这是因为您说的不是传递值,const filter = state.filter;而是传递引用。

例如,考虑一个书架,在图书馆的顶部有 JS 书。当您访问图书馆时,不会给您书籍的副本,而是给您书籍的位置。因此,如果您撕开书页并将其保留在原处。图书管理员还可以看到残页。但是,如果您不希望这种情况发生。您需要获取该书的副本并从中撕下页面,而书架上的书将保持原样。

因此,当您想要复制数据并将其存储在变量中时,ES6 引入了比早期笨拙的方法更简单的方法。所以这const filter = state.filter;

会变成这个const filter = [...state.filter]; // this makes copy of array

于 2020-03-04T10:55:37.563 回答
1

我发现了这个问题。useSelector 将返回嵌套对象的浅表副本,因此会发生突变。解决方案是手动进行深度复制。

于 2020-03-05T07:08:29.753 回答