在CoffeeScript中将对象数组映射到键/值对

时间:2011-12-01 21:32:32

标签: javascript jquery coffeescript

我有一个元素数组,我想应用一个映射来将其转换为单个对象上的键值对(模仿一个关联数组)。

Can destructuring assignment be used to effect a projection in CoffeeScript?中的方法似乎对我不起作用,因为它会产生一个简单的数组而不是键/值对。

我选择的语言是CoffeeScript或JavaScript。

一个例子:

[{name: 'a', value: 'b', other: 'c'}, {name: 'd', value: 'e', other: 'f'}]

应该转换为:

{
  a: 'b',
  d: 'e'
}

单线是首选。 ; - )

7 个答案:

答案 0 :(得分:78)

var arr = [{name: 'a', value: 'b', other: 'c'}, {name: 'd', value: 'e', other: 'f'}];

var obj = arr.reduce(function ( total, current ) {
    total[ current.name ] = current.value;
    return total;
}, {});

纯粹的javascript。它实际上只是一个衬里,它看起来很重要。

Array.prototype.reduce是ES5,但不难以垫片。这是一个示例垫片:

Array.prototype.reduce = function ( fun, initVal ) {
    var sum = initVal || this[ 0 ],
        i = 1, len = this.length;

    do {
        sum = fun.call( undefined, sum, this[i], i, this );
    } while ( ++i < len );

    return sum;
};

arr.reducearr.map的复杂版本,是arr.forEach的复杂版本。你可以这样做同样的效果:

var obj = {};
arr.forEach(function ( val ) {
    obj[ val.name ] = val.value;
});

//and using jQuery.each
var obj = {};
$.each( arr, function ( index, val ) {
    obj[ val.name ] = val.value;
});

//latter version in coffeescript:
obj = {}
$.each( arr, (index, val) ->
    obj[ val.name ] = val.value
)

答案 1 :(得分:19)

values = {}
values[name] = value for {name, value} in arr

或javascript:

var values = {}
arr.forEach(function(o){
    values[o.name] = o.value
})

这几乎就是CoffeeScript编写的内容。

答案 2 :(得分:12)

要修复语法错误,您必须将{ @name: @value }扩展为:

o = {}; o[@name] = @value; o

然后,您可以将对象与$.extend()和splat合并(使用空对象以避免意外扩展jQuery):

$.extend {}, $(row).children('input').map(() -> o = {}; o[@name] = @value; o)...

尽管如此,更简单的选择就是使用2-liner:

result = {}
$(row).children('input').each(() -> result[@name] = @value)

答案 3 :(得分:8)

或使用普通的ES6:

&#13;
&#13;
const old = [
  {name: 'a', value: 'b', other: 'c'}, 
  {name: 'd', value: 'e', other: 'f'}
]

const transformed = Object.assign(
  {}, 
  ...old.map(({name, value}) => ({ [name]: value }))
);

console.log(transformed);
&#13;
&#13;
&#13;

答案 4 :(得分:5)

使用Array.prototype.reduce()

var arrayOfObjects = [
              {name: 'a', value: 'b', other: 'c'}, 
              {name: 'd', value: 'e', other: 'f'}
            ];

arrayOfObjects.reduce(function(previousValue, currentValue, currentIndex) {
  previousValue[currentValue.name] = currentValue.value;
  return previousValue;
}, {})

答案 5 :(得分:1)

查看http://coffeescriptcookbook.com/chapters/arrays/creating-a-dictionary-object-from-an-array

  myArray = [{name: 'a', value: 'b', other: 'c'}, {name: 'd', value: 'e', other: 'f'}]
  dict = {}
  dict[obj['name']] = obj['value'] for obj in myArray when obj['name']?
  console.log(JSON.stringify(dict, 0, 2));

这正是你想要的。

答案 6 :(得分:0)

ES6单线:

const data = [{name: 'a', value: 97}, {name: 'b', value: 98}]

data.reduce((obj, e) => ({...obj, [e.name]: e.value}), {})