简体   繁体   English

JS / Lodash-替换多维对象中的值

[英]JS/Lodash - replace values in multidimensional object

I am looking for an efficient way to replace values within a multidimensional object using Lodash or even vanilla JS. 我正在寻找一种有效的方法来替换使用Lodash或什至普通JS的多维对象中的值。

I have an array with multidimensional objects of unknown depth like (simplified) 我有一个数组,其中包含未知深度的多维对象,例如(简化)

objects = [{
    id: 1,
    view: {
        id: 7
    }
}, {
    id: 2,
    view: {
        id: 9
    },
    childs: [{
        id: 3,
        view: {
            id: 3
        }
    }]
}];

Now I want to replace the value of view of each node with a named import reference stored in a separate object. 现在,我想用存储在单独对象中的命名导入引用替换每个节点的view值。 The references are accessible through the view.id as index of this object. 这些引用可以通过view.id作为此对象的索引进行访问。 So what I am trying to achieve is something like this 所以我想要实现的是这样的

views = {
    3: some,
    7: random,
    9: imports
};

objects = [{
    id: 1,
    view: views[7]
}, {
    ...
}];

Well I know how to iterate over a multidimensional object to achieve this manually but since I am working with large objects it would be nice if there would be a cleaner and more performant way using Lodash. 好吧,我知道如何遍历多维对象以手动实现此目的,但是由于我正在处理大型对象,因此,如果使用Lodash使用更干净,更高效的方法,那就太好了。

Does anybody have a genius solution? 有人有天才的解决方案吗?

Since lodash is just a utility layer written in JS, you're unlikely to get any performance gains over vanilla JS from using it. 由于lodash只是用JS编写的实用程序层,因此您不太可能通过使用它来获得优于普通JS的性能提升。

The function below is probably the fastest way to do what you want: it mutates the supplied objects instead of creating new ones, and does not iterate over every key. 下面的函数可能是最快的方法:它更改提供的对象而不是创建新的对象,并且不会遍历每个键。

function transform(arr) {
  arr.forEach(obj => {
    if (obj.hasOwnProperty('view')) obj.view = views[obj.view.id];
    if (obj.hasOwnProperty('childs')) transform(obj.childs);
  });
}

You can use a recursive _.transform() call to iterate and updated the objects' views: 您可以使用递归_.transform()调用来迭代和更新对象的视图:

 const fn = o => _.transform(o, (acc, v, k) => { // if key is view, and it and has an id value replace it with equivalent from views if(_.eq(k, 'view') && _.has(v, 'id')) acc[k] = _.get(views, v.id, v); // if it's an object transform it recursively else if (_.isObject(v)) acc[k] = fn(v); // assign primitives to accumulator else acc[k] = v; }); const objects = [{"id":1,"view":{"id":7}},{"id":2,"view":{"id":9},"childs":[{"id":3,"view":{"id":3}}]}]; const views = { 3: 'some', 7: 'random', 9: 'imports' }; const result = fn(objects); console.log(result); 
 <script src="https://cdnjs.cloudflare.com/ajax/libs/lodash.js/4.17.11/lodash.min.js"></script> 

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM