在 javascript 中使用 reduce 更改对象值

changing object value using reduce in javascript

我想使用 reduce 改变对象的值,但结果与我期望的不同。

const test = [
  {id: 'start', value: false},
  {id: 'reject', value: false},
];

let ress;
const showModal = (which) => {
  const res = test.reduce((res, s) => {
    ress = {id: s.id, value: s.id === which ? (s.value = true) : (s.value = false)};
    return ress;
  }, []);
}

showModal('start');
console.log(ress);

实际结果:

{
  "id": "reject",
  "value":false
}

预计:

[
  {id: 'start', value: true},
  {id: 'reject', value: false},
]

我不明白,为什么 {id:'start', value:true} 被删除并且 key改为string类型。

这是工作示例: https://codepen.io/seoulsaram/pen/RwpJRPv?editors=1010
谢谢!

const res = test.reduce((res, s) => {
  ress = {
    id: s.id,
    value: s.id === which ? (s.value = true) : (s.value = false)
  };
  return ress; // returning always last object as result.
}, []);

此代码不正确,您总是推送最新的对象。

它应该是这样的(这不是实现它的最佳方式,我只是让你的代码按你期望的方式工作):

const res = test.reduce((res, s) => {
  const ress = {
    id: s.id,
    value: s.id === which ? (s.value = true) : (s.value = false)
  }
  res.push(ress)
  return res; // return accumulator instead of object
}, []);

根据你的问题,看起来你在找 find 而不是 reduce。

这是更适合你的情况的方法(改变原始数组):

const test = [
  {id: 'start', value: false},
  {id: 'reject', value: false},
]

const showModal = (which) => {
  const found = test.find(e => e.id === which)
  found.value = true // it will mutate object in array
}

showModal('start')
console.log(test)

另一个解决方案(不改变原始数组):

const test = [
  {id: 'start', value: false},
  {id: 'reject', value: false},
]

const showModal = (which) => test.map(e => e.id === which ? ({...e, value: true}) : {...e})

const res = showModal('start')

console.log('res', res)
console.log('test', test)

有几件事需要注意。在 reduce 中,您应该 return 每次迭代的累积数组,但您 return 正在循环内创建变量(res 而不是 ress ) - 他们的名字非常相似,所以很容易打错字。

您的三元条件不正确(它导致了不正确的响应)并且可以简化。 value: s.id === which ? (s.value = true) : (s.value = false) 未正确评估 - 更容易做到 value: s.id === which

每次迭代我都使用 [...] 扩展运算符将累积数组与新对象连接起来。

const test = [{
    id: 'start',
    value: false
  },
  {
    id: 'reject',
    value: false
  },
];

let ress;
const showModal = (which) => {
  return test.reduce((res, s) => {
    ress = {
      id: s.id,
      value: s.id === which
    };
    return [...res, ress]
  }, []);
}

console.log(showModal('start'));