.forEach带有对象的数组将无法运行

时间:2018-10-16 16:09:29

标签: javascript arrays foreach

因此,现在我正在开发一个系统,学生可以将其标记放入表格中,该表格将运行一个函数,该函数将所有标记作为对象放置在数组中。

例如:{english_period1: 10, english_period2: 7} <示例

但是,如果我想运行array.prototype.forEach来对数组中的标记做些事情。它绝对不返回任何内容。 .forEach甚至不会运行。

这是脚本:

// Make new variable which will store the marks
let allMarks = [];

document.querySelector("#marks").addEventListener('submit', e => {
  e.preventDefault();

  //Execute for each input
  for(let i = 0; i < e.srcElement.length-1; i++){
    // Assign name and value
    const name = e.srcElement[i].name;
    const value = e.srcElement[i].value;

    //Check if value is a mark (number)
    if(value % 1 == 0 && value <= 10){
      //Assign mark
      allMarks[name] = value;
    }else{
      //Value is not a mark, check if it's a O, V or G
      if(value == "O" || value == "V" || value == "G"){
        allMarks[name] = value;
      }else{
        console.log("Niet toegestaan");
      }
    }
  }

  allMarks.forEach(mark => {
    console.log("hello world");
  });

},false);

它的作用是:

  1. 在用户标记并单击并提交表单后
  2. 浏览表单中的所有输入,并将名称和值作为对象放入数组中。
  3. 遍历数组中的所有内容,并在控制台中打印“ hello world”。

脚本的目标是计算学生成绩的平均值,并根据一些规则检查学生的成绩,以查看他们是否通过了学年。

我在做什么错?在包含对象的数组上使用array.prototype.forEach是否可行?我该如何优化这段代码?

谢谢!

答案

代替使用:allMarks[name] = value不会将项添加到数组allMarks = []中。使用allMarks.push({name: name, value: value});可以解决问题。因为现在它将在数组(对象)中添加一个项目,因此forEach可以遍历每个项目并像普通对象一样获取其值。

特别感谢:@mhodges

长答案

因此,在调试之后,编写了更多的脚本,我得出的结论是,按照以下答案中的建议使用对象是一种更好,更美观的选择。

可以使用objectName[variableName]向对象动态添加键。使用Object.keys(objectName)可以将键扔到数组中并在键上循环。在我的情况下,它将得到一个更漂亮的数据结构:

代替:[{field: "English", period: "period_1", mark: "7.5"}] 这将返回:

"English": {
 "period_1": 7.5,
 "period_2": 6.4
}

4 个答案:

答案 0 :(得分:2)

请注意,在这里很难说出您到底要做什么。如果需要 allMarks是一个数组,则需要将每个单独的mark添加到allMarks数组中,如下所示:

// Make new variable which will store the marks
let allMarks = [];

document.querySelector("#marks").addEventListener('submit', e => {
  e.preventDefault();

  //Execute for each input
  for(let i = 0; i < e.srcElement.length-1; i++){
    // Assign name and value
    const name = e.srcElement[i].name;
    const value = e.srcElement[i].value;
    // <-- create new mark object -->
    const newMark = {name: value}

    //Check if value is a mark (number)
    if(value % 1 == 0 && value <= 10){
      //Assign mark
      //<-- instead of allMarks[name] = value; -->
      //<-- you need to add the newMark to the allMarks array -->
      allMarks.push(newMark);
    }else{
      //Value is not a mark, check if it's a O, V or G
      if(value == "O" || value == "V" || value == "G"){
        //<-- same thing here -->
        allMarks.push(newMark);
      }else{
        console.log("Niet toegestaan");
      }
    }
  }

  allMarks.forEach(mark => {
    console.log("hello world");
  });

},false);

但是,您可以将allMarks设置为对象,然后将每个单独的mark设置为该对象的键值对。您仍然可以在对象中的键,值对之间循环,但是您将无法使用.forEach

您想要哪个?

答案 1 :(得分:1)

您的allMarks[name] = valueallMarks数组转换为具有文字属性(具有对象行为)的数组,.forEach()不能与此一起运行。您可以将allMarks用作对象:

let allMarksKeys = Object.keys(allMarks); 
allMarksKeys.forEach(key => // for example use allmarks[key] to access object elements)

答案 2 :(得分:1)

forEach将适用于数组,但数组索引应为数字(整数值)。

答案 3 :(得分:0)

我认为,如果将其创建为对象而不是数组,则更为简单。

例如

var allMarks = {};

您可以在其中使用

var marks;
marks.name = name;
marks.value = value;
allMarks.push(marks);

然后您就可以使用

allMarks.forEach(function(mark){
  console.log(mark.name);
  console.log(mark.value);
});