遍历缺少元素的数组

时间:2019-06-24 19:03:44

标签: javascript arrays vue.js

我有一个包含一些表格数据的JSON feed,并且正在使用Vue.js显示HTML表:

<tr v-for="row, index in content">
    <td class="index" v-text="index + 1"></td>
    <td v-for="column in row" v-text="column"></td>
</tr>

此提要为每一行返回一个数组,但是某些行具有命名键。使用这个简单的foreach循环,它会忽略键,这将生成一个表,该表不会以正确的方式显示数据。

如何使用密钥生成表?我已经考虑过使用highest value from the keys并使用Array.fill(),但我认为必须有更好的方法。

这是我的数据

{
  "content": [
    [
      "",
      "In scope:",
      "Not in scope:"
    ],
    [
      "Cars",
      "",
      "X"
    ],
    [
      "Bikes",
      "X",
      ""
    ],
    {
      "0": "Houses",
      "2": "X"
    }
  ]
}

请注意,这是虚构数据,实际数据可能会有所不同,因此我无法提供固定列数的解决方案。

实际输出:

|        | In scope: | Not in scope: |
|--------|-----------|---------------|
| Cars   |           | X             |
| Bikes  | X         |               |
| Houses | X         |

预期输出:

|        | In scope: | Not in scope: |
|--------|-----------|---------------|
| Cars   |           | X             |
| Bikes  | X         |               |
| Houses |           | X             |

5 个答案:

答案 0 :(得分:3)

看起来您的第一行是标题行。如果您可以接受以下内容作为长度真实性的来源,则可以创建一个简单的函数,该函数映射到数组上并为所有项目强制使用该长度。这将规范化项目,使其成为所有数组,填充孔,删除溢出长度的项目,并忽略对象上的非数字键:

let o = {
    "content": [
      [
        "",
        "In scope:",
        "Not in scope:"
      ],
      [
        "Cars",
        "",
        "X"
      ],
      [
        "Bikes",
        "X",
        "",
        "extra data!"          // < will be removed 
      ],
      {
        "non number": "huh?",  // < will be removef
        "0": "Houses",         // will fill in index 1 with undefined
        "2": "X",
        
      }
    ]
  }
const enforceLength = (l, arr) => arr.map(arr => Array.from({length: l, ...arr}))
let l = o.content[0].length

o.content = enforceLength(l, o.content)

console.log(o.content)

如果将其放在组件上的方法中,则可以使用类似以下内容的模板简单地调用它:

<tr v-for="row, index in normalize(content)">

答案 1 :(得分:0)

您使用Array#fill的想法对我来说似乎很好:您需要定义间隙的值(本例中为空字符串)。

但是,由于非数组对象的索引似乎总是数字的,因此找到最大键要容易一些。尽管ES6规范没有定义Object.keys返回值的顺序,但是当前所有的JS引擎都按数字顺序生成键(当键表示64位范围内的正整数时),因此您可以仅弹出最后一个值从它:

column in Object.assign(Array(+Object.keys(row).pop()+1).fill(""), row)

答案 2 :(得分:-1)

数据不是理想的,因为对象属性不采用编号索引(如果将其他数字声明为键,则对象显然不会“填补空白”)。您可以映射到一个新数组,在Vue组件的计算属性内的undefined上填充任何elem[1]

computed: {
  contentAsArrays() {
    return this.content.map(e => {
      if (e[1] === undefined) e[1] = "";
      return e;
    });
  },
},

并在您的模板中引用此计算属性:

<tr v-for="row, index in contentAsArrays">

答案 3 :(得分:-2)

  

通过这个简单的foreach循环,它会忽略键

假设您引用的是Array.prototype.forEach,则处理程序函数的第二个参数是迭代索引:

let arr = ['zero', 'one'];
arr[10] = 'ten';

arr.forEach((value, index) => console.log(value, index));

答案 4 :(得分:-2)

对我来说,我认为问题在于循环随着索引而移动,突然之间您没有该索引。

所以我相信发生的事情是:

它的循环索引= 0表示“自行车”

比循环索引= 1给出“ X”,

比循环索引= 2给出“”(对象中的第三个成员)

比起您给它一个两个成员的对象,它变成0到1

因此,请尝试将其另存为:

     - "0":"houses"
     - "1":""
     - "2":"X"