将数组重新映射到对象

时间:2015-01-28 00:04:22

标签: javascript arrays object dictionary

我有一个这样的数组:

var records = [{
  "field1": "dogs",
  "field2": "poodle"
}, {
  "field1": "dogs",
  "field2": "alsatian"
}, {
  "field1": "dogs",
  "field2": "chowchow"
}, {
  "field1": "dogs",
  "field2": "schnauzer"
}, {
  "field1": "cats",
  "field2": "siamese"
}, {
  "field1": "cats",
  "field2": "persian"
}, {
  "field1": "fish",
  "field2": "guppy"
}, {
  "field1": "fish",
  "field2": "tiger barb"
}]

我想迭代数组并创建一个新的数组Pets,以便我可以像

一样访问它
var Pets = [{
  "type": "dogs",
  "breeds": ["poodle", "alsatian", "chowchow", "schnauzer"]
}, {
  "type": "cats",
  "breeds": ["siamese", "persian"]
}, {
  "type": "fish",
  "breeds": ["guppy", "tiger barb"]
}]

我试着做一个for循环,但它没有工作,因为我在数组中使用i + 1

var thispet = {};
var Pets = [];

thispet.type = records[0].field1;
Pets.push(thispet);

for (i = 1; i < records.length; i++) {
  if (Pets[i - 1].type != records[i].field1) {
    thispet.type = records[i] field1;
    Pets.push(thispet);
  }
}

但不知何故,Pets [i-1] .type不被视为对象。

我想首先根据记录中的3种类型的宠物在阵列中创建3个对象,然后挑选出第二个品种(通过推入阵列应该更容易。我有一个大记录,所以一个循环会有很大帮助。

2 个答案:

答案 0 :(得分:2)

首先按类型对宠物进行分组然后将结果重新格式化为数组会更简单:

var group, pets = [], groups = {};
for (var i = 0; i < records.length; ++i) {
    group = groups[records[i].field1] || groups[records[i].field1] = [];
    group.push(records[i].field2);
}

for (var type in groups) {
    if (!groups.hasOwnProperty(type)) continue; // just to be on the safe side
    pets.push({ type: type, breeds: groups[type] });
}

.hasOwnProperty支票为standard procedure,以避免第三方代码出现令人不快的意外。

答案 1 :(得分:2)

ECMA5中可能的解决方案。

var records = [{
        "field1": "dogs",
        "field2": "poodle"
    }, {
        "field1": "dogs",
        "field2": "alsatian"
    }, {
        "field1": "dogs",
        "field2": "chowchow"
    }, {
        "field1": "dogs",
        "field2": "schnauzer"
    }, {
        "field1": "cats",
        "field2": "siamese"
    }, {
        "field1": "cats",
        "field2": "persian"
    }, {
        "field1": "fish",
        "field2": "guppy"
    }, {
        "field1": "fish",
        "field2": "tiger barb"
    }],

    x = records.reduce(function (acc, record) {
        if (!acc[record.field1]) {
            acc[record.field1] = [];
        }

        if (acc[record.field1].indexOf(record.field2) === -1) {
            acc[record.field1].push(record.field2);
        }

        return acc;
    }, {}),

    y = Object.keys(x).map(function (key) {
        return {
            type: key,
            breeds: this[key]
        };
    }, x);

document.getElementById('out').textContent = JSON.stringify(y, null, 2);
<pre id="out"></pre>