【问题标题】:How to iterate a Map() object?如何迭代 Map() 对象?
【发布时间】:2019-06-28 01:10:27
【问题描述】:

我有一个需要迭代的 Map() 对象,因此我可以获得星期几和选定的时间。下面的代码不起作用,因为Object.keys(newFieldReservationPrice).forEach 试图循环一个 Map() 对象,这似乎没有任何意义。那么,有没有更好的解决方案呢?

下面是代码:

handlePriceInput = (e, hour, day) => {
let value = e.target.value

const newFieldReservationPrice = this.state.newFieldReservationPrice
console.log('newFieldReservationPrice', newFieldReservationPrice) // A Map();
let map;

if (!newFieldReservationPrice instanceof Map) {
  console.log('!== Map')
  console.log('newFieldReservationPrice is a Map()? inside if ()', newFieldReservationPrice)
  if (newFieldReservationPrice[day] && newFieldReservationPrice[day][hour]) {
      newFieldReservationPrice[day][hour] = Number(value)
  } 
} else {
  map = new Map();
  console.log('map object', Object.keys(newFieldReservationPrice)) // logs map object []

  Object.keys(newFieldReservationPrice).forEach(key => {
    console.log('key', key)
      map.set(key, new Map(Object.entries(newFieldReservationPrice[key])));
  }); // This doesn't work
  console.log('Am I a Map()? map', map)

  const aux = map.get(day)
  console.log('aux day', aux) // A Map()
  aux.set(hour, Number(value)) // Comes as undefined || Cannot read property 'set' of undefined
  console.log('aux set', aux) // A Map()

  map.set(day, aux);
  console.log('what do I have?', map)

}
const isReservationPrice = !newFieldReservationPrice instanceof Map ? newFieldReservationPrice : map
console.log('isReservationPrice', isReservationPrice)

this.setState({
  newFieldReservationPrice: isReservationPrice
})
}

谢谢! :)

【问题讨论】:

标签: javascript reactjs


【解决方案1】:

Maps 提供了三种方法来获取其内容的迭代器:

  • keys - 迭代地图中的键
  • values - 迭代值
  • entries - 迭代键和值,为您提供 [key, value] 数组(这是默认值)

As Nina notes、Maps 还提供了forEach,它们循环遍历它们的内容,为回调提供值、键和映射作为参数。

使用适合您用例的一种。例如,如果您尝试替换 Object.keys,请使用 keys。同样,如果您想要地图中的条目(我注意到您在某一时刻使用Object.entries),请使用entries 或默认迭代器。

请注意,在您的代码中的一些地方,您似乎正在尝试使用[] 对地图进行索引。这对地图不起作用,您需要使用get。

这是一个使用默认迭代器的简单示例(也是您从entries 获得的那个):

const map = new Map();
map.set(1, "one");   // Could also include these when calling
map.set(2, "two");   // the constructor but I wanted to
map.set(3, "three"); // avoid any confusion

for (const [key, value] of map) { // Using the default iterator (could be `map.entries()` instead)
    console.log(`The value for key ${key} is ${value}`);
}

另请注意,您通过基于现有状态设置新状态而不使用setState 的回调版本来破坏one of React's rules。如果在设置新状态时需要使用现有状态,则必须使用回调版本:

this.setState(prevState => {
    // ...use `prevState` values (*not* `this.state`!) to create an object with
    // the updates, then return the object...
});

【讨论】:

  • 感谢您的解释。你的意思是像map.set(key, new Map(Object.entries(newFieldReservationPrice.get(key)))) ?
  • @RCohen - 你想用new Map(Object.entries(newFieldReservationPrice.get(key)))做什么?
  • 就像你说的那样,将 [key] 索引到地图中是行不通的。所以这里的想法是这样的: - 星期一: - 08:00: 10(在这一天和小时存储 10) 获取日期和小时,在这种情况下是 08:00 以保存新值。使用newFieldReservationPrice.forEach,我重复了几个小时
  • @RCohen - 是的,但你为什么要根据结果创建地图?但是,是的,我的意思是使用newFieldReservationPrice.get(key) 而不是newFieldReservationPrice[key]。 rest 对我来说没有意义,因为它假定存储在 newFieldReservationPrice 中的值不是映射(因为它使用 Object.entries),但您正在设置映射为 newFieldReservationPrice 中的值。
  • 这是因为这是来自 DB 作为对象的数据,我需要将其作为 Map 发回。这就是我这样做的原因。这是我找到的一种方式,也许不是最好的方式。 @T.J 克劳德
【解决方案2】:

您可以使用for of 迭代Map 对象:

for (const [key, value] of myMap) {
  console.log(key, value);
}

这与遍历条目相同:

for (const [key, value] of myMap.entries()) {
  console.log(key, value);
}

正如@Nina Scholz 所说,您可以在Map 原型(doc MDN)上使用forEach:

myMap.forEach((value, key, map) => {
  console.log(key, value);
}

【讨论】:

  • 我不知道为什么,Object.entries(newFieldReservationPrice).forEach 对我不起作用。 Object.keys(newFieldReservationPrice).forEach 也一样
【解决方案3】:

您可以使用Map#forEach 并直接迭代Map。

【讨论】:

    猜你喜欢
    • 1970-01-01
    • 1970-01-01
    • 2021-09-23
    • 2022-09-30
    • 2011-09-15
    • 2017-05-21
    • 2015-10-24
    • 2021-02-01
    • 2019-07-21
    相关资源
    最近更新 更多