【问题标题】:How to loop through an object by using the .forEach() method and store the result in a new array如何使用 .forEach() 方法遍历对象并将结果存储在新数组中
【发布时间】:2018-08-01 12:36:31
【问题描述】:

我想遍历对象 dogNames,并仅将我拥有的狗的名称返回到数组 myDogs 中。我希望 myDogs 在登录时显示为:

['Remington','Ruby','Chief','Link']

很可能,我不了解 .forEach() 方法的工作原理和/或如何操作对象。这是一些家庭作业帮助,我只是在几个小时后不理解 .forEach() 方法。感谢您的任何帮助。请指出正确的方向,我不希望其他人解决这个问题。

首先,这是我写的数组。

var dogNames = [
  {name: Kevin,     mine: false},
  {name: Remington, mine: true},
  {name: Bingo,     mine: false},
  {name: Ruger,     mine: false},
  {name: Ruby,      mine: true},
  {name: Gino,      mine: false},
  {name: Chief,     mine: true},
  {name: Watson,    mine: false},
  {name: Link,      mine: true}
];

这是我要将结果存储到的数组。

var myDogs = [];

这是我在谷歌之后尝试做的事情。

dogNames.forEach(function(mine){
    if(mine === true){
        myDogs.push(dogNames.name);
    }
});

【问题讨论】:

  • 你在寻找.filter() & .map()
  • 我希望我是。我需要使用 .forEach()

标签: javascript arrays object foreach


【解决方案1】:

与其解决它,我们来谈谈'forEach'

Array.prototype.forEach 的参数是一个函数。为数组中的每个项目调用此函数。

该函数接受一个表示数组中单个项目的参数。 所以如果我有:

var results = [];
var myArray = [1, 2, 3, 4, 5];

我有一个函数

function addOne(n) {
    results.push(n + 1)
}

我可以像这样在 myArray 上调用 forEach

myArray.forEach(addOne)

这将使我的结果数组看起来像

>>> [2, 3, 4, 5, 6]

我认为你的困惑是因为你正在处理一个对象数组,并且你试图迭代对象的属性 (mine: boolean) 而不是对象本身 ({name: string, mine:boolean})

在你的情况下,你可以有一个这样的数组:

var secondResults = []
var myObjArray = [{a: 1}, {a: 2}, {a:3}]

还有另一个功能

function addOneToObj(obj) {
   obj.a = obj.a + 1;
   secondResults.push(obj)
}

你可以在上面调用 forEach

 myObjArray.forEach(addOneToObj)

secondResults 看起来像

>>> [{a: 2}, {a: 3}, {a: 4}]

var results = [];
var myArray = [1, 2, 3, 4, 5];
function addOne(n) {
  results.push(n + 1)
}

myArray.forEach(addOne)
console.log(results); //[2, 3, 4, 5, 6]

var secondResults = []
var myObjArray = [{a: 1}, {a: 2}, {a:3}]
  
function addOneToObj(obj) {
   obj.a = obj.a + 1;
   secondResults.push(obj)
}

myObjArray.forEach(addOneToObj)

console.log(secondResults); //[{a: 2}, {a: 3}, {a: 4}

 

关于为什么这是一种不好的方法的一些说明

Array.prototype.forEach 通常用于副作用。 Array.prototype.forEach 实际上并没有返回任何东西。如果您期望以某种方式更改数组中的项目的最终结果,则应改用 .map。

这会将我们之前的示例简化为:

    
    var myArray = [1, 2, 3, 4, 5];
    function addOne(n) {
      return n + 1
    }

    var results = myArray.map(addOne)
    console.log(results); //[2, 3, 4, 5, 6]

    
    var myObjArray = [{a: 1}, {a: 2}, {a:3}]
      
    function addOneToObj(obj) {
       obj.a = obj.a + 1;
       return (obj)
    }

    var secondResults = myObjArray.map(addOneToObj)

    console.log(secondResults); //[{a: 2}, {a: 3}, {a: 4}]

【讨论】:

    【解决方案2】:

    在您的逻辑中,当您执行push 时,您需要传递mine.name 作为参数,而不是dogNames.name

    在您的forEach 中,当您输入mine 时,您会收到{ name: 'Kevin', mine: false } 之类的对象,因此,您需要指定要检查的属性,就像在您的if 语句中一样。

    var dogNames = [
      {name: 'Kevin',     mine: false},
      {name: 'Remington', mine: true},
      {name: 'Bingo',     mine: false},
      {name: 'Ruger',     mine: false},
      {name: 'Ruby',      mine: true},
      {name: 'Gino',      mine: false},
      {name: 'Chief',     mine: true},
      {name: 'Watson',    mine: false},
      {name: 'Link',      mine: true}
    ];
    
    var myDogs = [];
    
    dogNames.forEach(mine => (mine.mine && myDogs.push(mine.name)));
    

    【讨论】:

      【解决方案3】:

      带函数reduce

      var dogNames = [  {name: 'Kevin',     mine: false},  {name: 'Remington', mine: true},  {name: 'Bingo',     mine: false},  {name: 'Ruger',     mine: false},  {name: 'Ruby',      mine: true},  {name: 'Gino',      mine: false},  {name: 'Chief',     mine: true},  {name: 'Watson',    mine: false},  {name: 'Link',      mine: true}];
      
      var myDogs = dogNames.reduce((a, d) => {
        if (d.mine) a.push(d.name);
        return a;
      }, []);
      console.log(myDogs);
      .as-console-wrapper { max-height: 100% !important; top: 0; }

      【讨论】:

        【解决方案4】:

        在你的方法中:

        dogNames.forEach(function(mine){
            if(mine === true){
                myDogs.push(dogNames.name);
            }
        });
        

        mine 基本上是数组的单个元素,因此要访问该元素的属性,您将需要点符号。您可以使用mine.mine 访问矿区,使用mine.name 访问名称。现在只需进行正确的比较并在数组中推送正确的值。

        虽然,您不需要使用 .forEach(),但更简单的方法是使用 .filter().map() 从数组中返回 name 键的值,以获得我的 true。

        dogNames.filter(el => el.mine).map( el => el.name); 
        

        查看下面的完整代码。

        var dogNames = [
          {name: "Kevin",     mine: false},
          {name: "Remington", mine: true},
          {name: "Bingo",     mine: false},
          {name: "Ruger",     mine: false},
          {name: "Ruby",      mine: true},
          {name: "Gino",      mine: false},
          {name: "Chief",     mine: true},
          {name: "Watson",    mine: false},
          {name: "Link",      mine: true}
        ];
        
        var myDogs = dogNames.filter(el => el.mine).map( el => el.name);
        console.log(myDogs)

        【讨论】:

          【解决方案5】:

          您可以过滤数组并映射过滤后数组的名称。

          var dogNames = [{ name: 'Kevin', mine: false }, { name: 'Remington', mine: true }, { name: 'Bingo', mine: false }, { name: 'Ruger', mine: false }, { name: 'Ruby', mine: true }, { name: 'Gino', mine: false }, { name: 'Chief', mine: true }, { name: 'Watson', mine: false }, { name: 'Link', mine: true }],
              myDogs = dogNames
                  .filter(({ mine }) => mine)
                  .map(({ name }) => name)
               
          console.log(myDogs);

          【讨论】:

            【解决方案6】:

            var dogNames = [
              {name: 'Kevin',     mine: false},
              {name: 'Remington', mine: true},
              {name: 'Bingo',     mine: false},
              {name: 'Ruger',     mine: false},
              {name: 'Ruby',      mine: true},
              {name: 'Gino',      mine: false},
              {name: 'Chief',     mine: true},
              {name: 'Watson',    mine: false},
              {name: 'Link',      mine: true}
            ];
            
            var myDogs = [];
            
            dogNames.forEach(function(dog){
                if(dog.mine === true){
                    myDogs.push(dog.name);
                }
            });
            
            console.log(myDogs);

            【讨论】:

              【解决方案7】:

              当您遍历 dogNames 时,function 中的参数是每个对象。所以你认为mine实际上是整个对象。

              改为:

              dogNames.forEach(dogName => {
                  if(dogName.mine === true){
                      myDogs.push(dogName.name);
                  }
              });
              

              【讨论】:

              • dogName.mine 是一个布尔值,你不需要和true比较
              • 这正是我不理解的,谢谢。
              • 没问题,Ele是对的,你可以用if(dogName.mine)
              • 我将在几天后参加代码训练营,但不明白事情是如何运作的。您能否解释一下,或者只是提供一个关于如何使用布尔值的链接?
              • 至少在您当前问题的上下文中:对于if 语句,如果括号之间的代码计算结果为true,它将执行括号之间的代码。 mine 的值都是truefalse,不需要进一步评估。你现在说的是if(true === true),而实际上你只需要if(true)
              【解决方案8】:
              var myDogs = dogNames.filter(x => x.mine).map(x => x.name);
              

              【讨论】:

                猜你喜欢
                • 2015-07-31
                • 2021-07-03
                • 1970-01-01
                • 1970-01-01
                • 2020-05-14
                • 1970-01-01
                • 1970-01-01
                • 2021-03-06
                • 1970-01-01
                相关资源
                最近更新 更多