Skip to content
Advertisement

Converting csv file data to a JavaScript dictionary

CSV File Data:

parent_name, child_name
A1, A2
A1, A3
A1, A4
A1, A5
A2, A12
A2, A16
A2, A18
A2, A19

Output: Javascript Object to be made

{
name: A1,
children: [
            {
             name: A2,
             children: [
                        {
                         name: A4,
                         children: []
                        }
                       ]
            },
            {
             name: A3,
             children: []
            }
}

Basically, I have to convert a CSV file to make a Tree in d3. I am wondering how to make the dictionary required from the CSV file

d3.csv("test1.csv").then(function (data) {
        var dataset = {};
        data.forEach(function (d,i){
            console.log(d.parent_name, d.child_name);
            if(i === 0){
                dataset["name"]  = d.parent_name;
                dataset["children"] = [];
            }
            if (dataset["name"] === d.parent_name){
                dataset.children.push(NodeMaker(d.child_name))
            }
        });
        function NodeMaker(name){
            return {"name": name, "children": []};
        }
        console.log(dataset);
    });

So this is the code, I have which only make a dictionary-like, It doesn’t go deeper than the 1st level of the root node

{
name: A1,
children: [
           {
             name: A2,
             children: []
           },
           {
             name: A3,
             children: []
           }
           ]
}

Advertisement

Answer

Currently you’re only checking to see if the node matches the root (first) node. One idea might be to traverse the existing tree and check if the parent node you want to add already exists and then add a child to it. But this has some issues: it requires going back through the data, so it’s inefficient; and what happens if you encounter a parent_node that isn’t part of the tree yet? As vicatcu pointed out, a more efficient (and robust) way would be to create nodes as you encounter them and keep them in a dictionary/lookup object.

It could look something like this:

var sampleData = [
    { parent_name: 'A1', child_name: 'A2' },
    { parent_name: 'A1', child_name: 'A3' },
    { parent_name: 'A1', child_name: 'A4' },
    { parent_name: 'A1', child_name: 'A5' },
    { parent_name: 'A2', child_name: 'A12' },
    { parent_name: 'A2', child_name: 'A16' },
    { parent_name: 'A2', child_name: 'A18' },
    { parent_name: 'A2', child_name: 'A19' }
]

// if loading from a file, use this line instead to load data
// d3.csv("test1.csv").then(function (data) {
Promise.resolve(sampleData).then(function (data) {
    var lookup = {};
    data.forEach(function (d,i) {
        var parentNode = getNode(d.parent_name);
        parentNode.children.push(getNode(d.child_name));
    });
    function getNode(name) {
        if (!lookup[name]) {
            // if the node doesn't exist, make it
            lookup[name] = NodeMaker(name);
        }
        return lookup[name];
    }
    function NodeMaker(name){
        return {"name": name, "children": []};
    }
    // if the first parent node is the root, it represents the whole tree
    var tree = lookup[data[0].parent_name];
    console.log(tree);
    // do something with `tree`
});
User contributions licensed under: CC BY-SA
10 People found this is helpful
Advertisement