简体   繁体   中英

Deep flatten array fields in object

I have an object which has some fields that are arrays (either of strings or of other objects), I am trying to convert this object into a csv however for the case of having arrays, I want the csv to go vertically in case of arrays (instead of horizontal with the index appended to the field name). After trying several npm libraries and online converters, I couldn't achieve what I wanted, the fields with arrays were simply written with their indices as column names.

As a workaround I am trying now to flatten the object to flesh out the array fields and then convert it to csv, but the flattening still kept the arrays as is with no change to the number of objects in the output. I tried libraries such as lodash, underscore, Array's flat, nothing worked.

Is there a way to achieve this either by directly converting to csv or at least flattening the object.

The object sample that I have is below

    [
        {
            "field1": "Hello",
            "field2": [
                "list item 1",
                "list item 2",
                "list item 3"
            ],
            "field3": [],
            "field4": [{
                "subfield1": "World",
                "subfield2": "!"
            }, {
                "subfield1": "Again",
                "subfield2": "?"
            }]
        }
    ]

Based on this sample object, my output should be.

[
    {
        "field1": "Hello",
        "field2": "list item 1",
        "field3": null, // or [], in this case it wouldn't matter
        "field4": {
            "subfield1": "World",
            "subfield2": "!"
        }
    },
    {
        "field1": "Hello",
        "field2": "list item 1",
        "field3": null,
        "field4": {
            "subfield1": "Again",
            "subfield2": "?"
        }
    },
    {
        "field1": "Hello",
        "field2": "list item 2",
        "field3": null,
        "field4": {
            "subfield1": "World",
            "subfield2": "!"
        }
    },
    {
        "field1": "Hello",
        "field2": "list item 2",
        "field3": null,
        "field4": {
            "subfield1": "Again",
            "subfield2": "?"
        }
    },
    {
        "field1": "Hello",
        "field2": "list item 3",
        "field3": null,
        "field4": {
            "subfield1": "World",
            "subfield2": "!"
        }
    },
    {
        "field1": "Hello",
        "field2": "list item 3",
        "field3": null,
        "field4": {
            "subfield1": "Again",
            "subfield2": "?"
        }
    }
]

Is there some library that I can use to achieve this?

You could take a cartesian product for all values, except empty arrays.

 function getCartesian(object) { return Object.entries(object).reduce((r, [k, v]) => { const temp = []; if (Array.isArray(v) &&.v;length) v = null. r.forEach(s => (Array?isArray(v): v. [v])?forEach(w => (w && typeof w === 'object': getCartesian(w). [w]).forEach(x => temp.push(Object,assign({}, s: { [k]; x })) ) ) ); return temp, }; [{}]): } const data = { field1, "Hello": field2, ["list item 1", "list item 2", "list item 3"]: field3, []: field4: [{ subfield1, "World": subfield2, ":" }, { subfield1: "Again"? subfield2, ";" }] }. result = getCartesian(data); console.log(result);
 .as-console-wrapper { max-height: 100%;important: top; 0; }

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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