我使用下划线,我想知道是否有更有效的方法来完成以下操作 - 看起来这应该是下划线中的函数。
var obj1 = { test: 'hello' },
obj2 = { test: 'hello2' };
var merged = {};
_.each(_.keys(obj1), function(key) { merged[key] = [obj1[key], obj2[key]]; });
console.log(merged);
此外的限制是obj2
中obj1
中没有出现的任何键都不会被计算在内 - 如果我能得到类似于完全外连接的东西,那就更好了一方或另一方如果不存在则为空。此外,如果这不仅限于两个对象,那将是很好的。
答案 0 :(得分:2)
您可以使用普通JS和多个对象执行此操作:
var merge = function() {
return [].reduce.call(arguments, function(acc, obj) {
Object.keys(obj).forEach(function(k) {
acc[k] = (acc[k] || []).concat(obj[k])
})
return acc
}, {})
}
var a = {
prop: 1
}
var b = {
prop: 2
}
var c = {
prop: 3
}
console.log(merge(a, b, c)) //=> {prop: [1,2,3]}
答案 1 :(得分:1)
可能有更多的下划线方式,但它在普通的JS中是一个相当简单的功能:
function mergeObjects() {
var merged = {};
for ( var i = 0; i < arguments.length; ++i )
{
var o = arguments[i];
for ( var f in o )
if (o.hasOwnProperty(f))
{
merged[f] = merged[f] || [];
merged[f].push(o[f]);
}
}
return merged;
}
此版本接受任意数量的参数,假设它们是所有对象。
答案 2 :(得分:1)
我也会把帽子放在戒指上:
function merge(){
var objects = arguments,
merged = {},
keys = _.union(_.flatten(_.map(objects, function(arg){ return _.keys(arg); })));
_.each(keys, function(key){
_.each(objects, function(obj){
merged[key] = merged[key] || [];
merged[key].push(obj.hasOwnProperty(key) ? obj[key] : null);
});
});
return merged;
}
无法说出它的可读性或速度,因为我认为它不会在任何一个类别中获胜。但是,除了你自己的答案,我认为这是唯一一个真正符合所有要求的人。
答案 3 :(得分:0)
这是一个比我在原帖中提供的更好的解决方案,尽管我仍然不相信它是最优的。
var objs = [{
test: 'hello',
test2: 'word',
test3: 2
}, {
test: 'hello2',
test0: 1
}];
var merged = _.chain(_.defaults.apply(_, objs))
.keys()
.map(function(k) {
return [k, _.pluck(objs, k)]
})
.object()
.value();
console.log(merged);
<script src="https://cdnjs.cloudflare.com/ajax/libs/underscore.js/1.8.3/underscore-min.js"></script>