LoDash - 如何通过公用键将一个 collections 值推送到另一个值

LoDash - How to push one collections values into another via common key

我有两个collections.

var a = 
[
 {unique_id: "001", state: "CO"},
 {unique_id: "001", state: "TX"},
 {unique_id: "001", state: "CC"},
 {unique_id: "002", state: "CC"},
 {unique_id: "002", state: "NY"}
]

var b = 
[
 {unique_id: "001", states:[]},
 {unique_id: "002", states:[]}
]

我想得到:

var b = 
[
 {unique_id: "001", states:["CO","TX","CC"]},
 {unique_id: "002", states:["CC","NY"]}
]

我应该提到,"b" 数组必须保持与它相同的顺序,并且一些 unique_id 没有值。

我一直在尝试使用 LoDash https://lodash.com/ - 所以如果有人能用 LoDash 解决这个问题那就太棒了!

此解决方案的时间复杂度不是最优的 ( O(n^2) ),但它可能会帮助您想出将值推入 "b":

的匹配方法
_.forEach(a, function(element1){
  _.forEach(b, function(element2){
    if (element2.unique_id === element1.unique_id) {
     element2.states.push(element1.state);
    }
  });
});

也许更好的解决方案是使用 lodash 的 _.indexBy 方法通过对象的唯一 ID 为 b 中的对象编制索引。例如,您可以按如下方式为 b 中的对象编制索引:

var c = _.indexBy(b, 'unique_id')

这将导致:

{001:{unique_id: "001", states:[]}, 002: {unique_id: "002", states:[]}}

由于 c 数组中的对象指向内存中与 b 数组中相同的对象,我们可以直接改变 c 中的对象,b 将引用内存中那些更新的对象。所以:

_.forEach(a, function(element1){
  if (element1.unique_id in c) {
    c[element1.unique_id].states.push(element1.state);
  }
})

现在,如果我们看一下 b 数组,我们会看到值为:

var b = 
[
 {unique_id: "001", states:["CO","TX","CC"]},
 {unique_id: "002", states:["CC","NY"]}
]

这个解决方案的时间复杂度应该接近于 O(n),这比使用嵌套 _.forEach 方法要好得多。代码片段:

var a = 
[
 {unique_id: "001", state: "CO"},
 {unique_id: "001", state: "TX"},
 {unique_id: "001", state: "CC"},
 {unique_id: "002", state: "CC"},
 {unique_id: "002", state: "NY"}
];

var b = 
[
 {unique_id: "001", states:[]},
 {unique_id: "002", states:[]}
];

var c = _.indexBy(b, 'unique_id');

_.forEach(a, function(element1){
  if (element1.unique_id in c) {
    c[element1.unique_id].states.push(element1.state);
  }
});

document.writeln(JSON.stringify(b))
<script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/3.9.3/lodash.js"></script>

groupBy() and map() 是你的朋友:

_(a).groupBy('unique_id')
    .map(function(item, key) {
        return {
            unique_id: key,
            states: _.pluck(item, 'state')
        };
    })
    .value()

您基本上是按 unique_id 对状态进行分组,然后将该对象映射到一个数组,其中每个项目都具有您需要的结构。