Process JSON to create the hierarchical relationship

自闭症网瘾萝莉.ら 提交于 2019-12-23 20:26:08

问题


I am sorry if I am asking a foolish question but this is something which is troubling me and I am not able to find the best solution of it yet.

I have a JSON Data which look like this:

{
    "my_data": [
        {
            "name": "bugs_db",
            "type": "database",
            "children": [
                {
                    "name": "oss",
                    "type": "ui"
                },
                {
                    "name": "dashboard",
                    "type": "ui"
                },
                {
                    "name": "dev-dash",
                    "type": "ui"
                }
            ]
        },
        {
            "name": "oss",
            "type": "ui",
            "children": [
                {
                    "name": "active-directory",
                    "type": "nfs"
                },
                {
                    "name": "passive-directory",
                    "type": "FAT32"
                }
            ]
        },
        {
            "name": "jira_db",
            "type": "database",
            "children": [

            ]
        },
        {
            "name": "active_directory",
            "type": "nfs",
            "children": []
        }
    ]
}

I am trying to process this data such that, for a selected root (name), there will be hierarchical relationship of the data. For exa. the result data should look like this (if I have selected "bugs_db").

{
    "name": "bugs_db",
    "kind": "root",
    "children": [
        {
            "name": "oss",
            "type": "ui",
            "children": [
                {
                   "name": "active-directory",
                   "type": "nfs",
                   "children": []
                },
                {
                    "name": "passive-directory",
                    "type": "FAT32"
                }
            ]
        },
        {
            "name" : "dashboard",
            "type": "ui"
        },
        {
            "name": "dev-dash",
            "type": "ui"
        }
    ]
}

I have tried to write code which works till 1st level..

var selectedApp = "bugs_db";
var all_data = {
  name: selectedApp,
  type: "root",
  children: []
}
for(var i = 0; i < data.my_data.length; i++){
  var currentObj = data.my_data[i];
  if(currentObj.name == selectedApp && currentObj.children.length){
      for(var j = 0; j < currentObj.children.length; j++){
           let childObj = {
              name: currentObj.children[j].name,
              type: currentObj.children[j].type,
              children: []
           }
           allData.children.push(childObj);
      }
  }
}

But the above code doesn't makes the further hierarchy. I know this can be done using some kind of recursive function.. but I am not sure how.. may be thats why falling into infinite loop.

Can any one please help me here. Please let me know if you need any more information.


回答1:


You could take a map and a recursive approach by building new objects.

function getTree(name) {
    var object = map.get(name);
    return object && Object.assign({}, object, { children: object.children.map(o => Object.assign({}, o, getTree(o.name))) });
}

var object = { my_data: [{ name: "bugs_db", type: "database", children: [{ name: "oss", type: "ui" }, { name: "dashboard", type: "ui" }, { name: "dev-dash", type: "ui" }] }, { name: "oss", type: "ui", children: [{ name: "active-directory", type: "nfs" }, { name: "passive-directory", type: "FAT32" }] }, { name: "jira_db", type: "database", children: [] }, { name: "active_directory", type: "nfs", children: [] }] },
    map = new Map(object.my_data.map(o => [o.name, o]));

console.log(getTree("bugs_db"));
.as-console-wrapper { max-height: 100% !important; top: 0; }

With circular check.

function getTree(name, visited = new Set) {
    var object = map.get(name);

    if (!object) {
        return object;
    }

    if (visited.has(name)) {
        return object && Object.assign({}, object, { circular: true, children: [] });
    }

    visited.add(name);
    return Object.assign({}, object, { children: object.children.map(o => Object.assign({}, o, getTree(o.name, visited))) });
}

var object = { my_data: [{ name: "bugs_db", type: "database", children: [{ name: "oss", type: "ui" }, { name: "dashboard", type: "ui" }, { name: "dev-dash", type: "ui" }, { name: "bugs_db", type: "exception" }] }, { name: "oss", type: "ui", children: [{ name: "active-directory", type: "nfs" }, { name: "passive-directory", type: "FAT32" }] }, { name: "jira_db", type: "database", children: [] }, { name: "active_directory", type: "nfs", children: [] }] },
    map = new Map(object.my_data.map(o => [o.name, o]));

console.log(getTree("bugs_db"));
.as-console-wrapper { max-height: 100% !important; top: 0; }



回答2:


You can do:

const selectedApp = "bugs_db";
const data = {"my_data": [{"name": "bugs_db","type": "database","children": [{"name": "oss","type": "ui"},{"name": "dashboard","type": "ui"},{"name": "dev-dash","type": "ui"}]},{"name": "oss","type": "ui","children": [{"name": "active-directory","type": "nfs"},{"name": "passive-directory","type": "FAT32"}]},{"name": "jira_db","type": "database","children": []},{"name": "active_directory","type": "nfs","children": []}]};
const all_data = {
  name: selectedApp,
  type: "root",
  children: []
};

all_data.children = data.my_data
  .find(el => el.name == selectedApp).children
  .map(obj => {
    const found = data.my_data.find(el => el.name == obj.name);
    if (found && found.children) {
      obj.children = found.children;
    }
    return obj;
  });

console.log(all_data);
.as-console-wrapper { max-height: 100% !important; top: 0; }



回答3:


You want soemthing like this?

var data = {
    "my_data": [
        {
            "name": "bugs_db",
            "type": "database",
            "children": [
                {
                    "name": "oss",
                    "type": "ui"
                },
                {
                    "name": "dashboard",
                    "type": "ui"
                },
                {
                    "name": "dev-dash",
                    "type": "ui"
                }
            ]
        },
        {
            "name": "oss",
            "type": "ui",
            "children": [
                {
                    "name": "active-directory",
                    "type": "nfs"
                },
                {
                    "name": "passive-directory",
                    "type": "FAT32"
                }
            ]
        },
        {
            "name": "jira_db",
            "type": "database",
            "children": [

            ]
        },
        {
            "name": "active-directory",
            "type": "nfs",
            "children": [
            {
            	"name": "ubuntu",
            	"type": "os"
            }
            ]
        },
        {
            "name": "ubuntu",
            "type": "os",
            "children": []
        }
    ]
};
var selectedApp = "bugs_db";
var all_data = {
  name: selectedApp,
  type: "root",
  children: []
}
for(var i = 0; i < data.my_data.length; i++){
  var currentObj = data.my_data[i];
  if(currentObj.name == selectedApp && currentObj.children.length){
      for(var j = 0; j < currentObj.children.length; j++){
           let childObj = {
              name: currentObj.children[j].name,
              type: currentObj.children[j].type,
           }
           findChildren(childObj)
           all_data.children.push(childObj);
      }
  }
}

function findChildren(obj){
	obj.children = data.my_data.filter(o => o.name == obj.name && o.type == obj.type ).map(o => o.children)[0];
  if (obj.children)
  obj.children.forEach(child => {
  	findChildren(child);
  });
}




console.log(all_data)


来源:https://stackoverflow.com/questions/50490287/process-json-to-create-the-hierarchical-relationship

易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!