0

如何将一组对象的树结构克隆到另一个对象,在 TypeScript 中对克隆的对象具有不同或更少的属性?例如关于这个:

[
   {
      "name":"root_1",
      "extradata":"whatever",
      "anArray":[
         { "id":1, "value":"test" },
         { "id":1, "value":"test" }
      ],
      "anObject":{ "id":1, "value":"test" },
      "children":[
         {
            "name":"child_1",
            "extradata":"whatever",
            "anArray":[],
            "anObject":{},
            "children":[
               {
                  "name":"root_1",
                  "extradata":"whatever",
                  "anArray":[],
                  "anObject":{},
                  "children":[]
               },
               {
                  "name":"root_1",
                  "extradata":"whatever",
                  "anArray":[],
                  "anObject":{},
                  "children":[]
               }
            ]
         }
      ]
   },
   {
      "name":"root_2",
      "extradata":"whatever",
      "anArray":[],
      "anObject":{},
      "children":[]
   }
]

我需要它的克隆,但不是“命名”属性“标签”,而是“extradata”=“key”并且没有“anArray”和“anObject”。像这样:

[
   {
      "label":"root_1",
      "key":"whatever",
      "children":[
         {
            "label":"child_1",
            "key":"whatever",
            "children":[
               {
                  "label":"root_1",
                  "key":"whatever",
                  "children":[]
               },
               {
                  "label":"root_1",
                  "key":"whatever",
                  "children":[]
               }
            ]
         }
      ]
   },
   {
      "label":"root_2",
      "key":"whatever",
      "children":[]
   }
]

我需要克隆它,以使用它作为primeng树组件的数据格式。

我正在尝试类似的东西

this.myTree = tree.map((m, index) => Object.assign({}, {
                                label: m.name,
                                key: m.extradata,
                                children: m.children
                            }));

但孩子们并没有遵循相同的形状。

4

2 回答 2

1

我会通过首先为有问题的输入和输出类型定义接口来做到这一点:

interface InputTree {
  name: string,
  extradata: string,
  anArray: any[],
  anObject: object,
  children: InputTree[]
}

interface OutputTree {
  label: string,
  key: string,
  children: OutputTree[];
}

根据该定义,您的输入看起来像是一个InputTree[],并且您想要生成一个OutputTree[]. 树是递归的,因此您应该编写一个treeMap()对 an 进行操作的函数,InputTree[]然后在数组children中的 each上递归调用自身。InputTree像这样:

const treeMap = (inputTree: InputTree[]): OutputTree[] => inputTree.map(t => ({
  label: t.name,
  key: t.extradata,
  children: treeMap(t.children)
}));

const actual = treeMap(tree);

您可以验证这是否会产生您期望的输出:

console.log(JSON.stringify(expected)===JSON.stringify(actual)); // true

Playground 代码链接

于 2020-10-14T16:21:34.153 回答
1

我不确定您是否可以使用 3rd 方库 - 但您听说过loadsh吗?有很多关于如何实现这一目标的例子(:

第一个例子

第二个例子

如果你不能使用它,我会深入研究代码,看看他们是如何实现它的(:

于 2020-10-14T16:10:59.067 回答