简体   繁体   English

如何根据可用键和用户输入创建新的合并 javascript 对象

[英]How to create a new merged javascript object based on available keys and user's input

If I have available keys like:如果我有可用的密钥,例如:

[   
    "cars[].model",
    "cars[].make",
    "cars[].year",
    "toys.color",
    "toys.type[].brand",
    "toys.type[].price",
    "id",
    "books[].publisher[].authors[]"
]

where cars[].model represents that cars is an array of objects with model as one of the keys.其中cars[].model 表示cars 是一个对象数组,其中model 作为键之一。

And if the input is:如果输入是:

{
    "cars": [
        {
            "make": "Audi"
        },
        {
            "model": "A8",
            "year": "2007"
        }
    ],
    "id": "xyz",
    "extra": "test",
    "toys": {
        "color": "Black",
        "type": [
            {
                "price": "$100"
            }
        ]
    }
}

How do I create an object based on these available keys and the input object?如何根据这些可用键和输入对象创建对象?

Targeted output:目标输出:

{
    "cars": [
        {
            "model": "",
            "make": "Audi",
            "year": ""
        },
        {
            "model": "A8",
            "make": "",
            "year": "2007"
        }
    ],
    "toys": {
        "color": "Black",
        "type": [
            {
                "brand": "",
                "price": "$100"
            }
        ]
    },
    "id": "xyz",
    "books": [
        {
            "publisher": [
                {
                    "authors": []
                }
            ]
        }
    ],
    "extra": "test"
}

If the available keys doesn't exist, the value is empty.如果可用的键不存在,则值为空。

I have tried flattening/unflattening the nested object, but in vain.我曾尝试展平/取消展平嵌套对象,但徒劳无功。

Any help would be appreciated.任何帮助,将不胜感激。

This is a job for recursion .这是递归的工作。 I defined a function, addKeysRec , that would add in the missing elements in the input array:我定义了一个函数addKeysRec ,它将添加input数组中缺少的元素:

function addKeysRec(input, keyArray, recursiveCalls=0) {
    if (recursiveCalls == keyArray.length) return
    const k = keyArray[recursiveCalls]
    if (k == "[]") {
        if (!input.length && recursiveCalls + 1 < keyArray.length) input.push({})
        input.forEach(s => addKeysRec(s, keyArray, recursiveCalls + 1))            
    } else {
        if (!input.hasOwnProperty(k)) {
            if (keyArray[recursiveCalls + 1] == null) input[k] = ''
            else if (keyArray[recursiveCalls + 1] == '[]') input[k] = []
            else input[k] = {}
        }
        addKeysRec(input[k], keyArray, recursiveCalls + 1)
    }
}

The function in action:作用中的函数:

const keys = [   
    "cars[].model",
    "cars[].make",
    "cars[].year",
    "toys.color",
    "toys.type[].brand",
    "toys.type[].price",
    "id",
    "books[].publisher[].authors[]"
]

const input = {
    "cars": [
        {
            "make": "Audi"
        },
        {
            "model": "A8",
            "year": "2007"
        }
    ],
    "id": "xyz",
    "extra": "test",
    "toys": {
        "color": "Black",
        "type": [
            {
                "price": "$100"
            }
        ]
    }
}

function addKeysRec(input, keyArray, recursiveCalls=0) {
    if (recursiveCalls == keyArray.length) return
    const k = keyArray[recursiveCalls]
    if (k == "[]") {
        if (!input.length && recursiveCalls + 1 < keyArray.length) input.push({})
        input.forEach(s => addKeysRec(s, keyArray, recursiveCalls + 1))            
    } else {
        if (!input.hasOwnProperty(k)) {
            if (keyArray[recursiveCalls + 1] == null) input[k] = ''
            else if (keyArray[recursiveCalls + 1] == '[]') input[k] = []
            else input[k] = {}
        }
        addKeysRec(input[k], keyArray, recursiveCalls + 1)
    }
}

 keys.forEach(key => {
    keyArray = key.replace(/\[\]/g, '.[]').split(".")
    addKeysRec(input, keyArray)
})

console.log(input)

Output:输出:

{
    "cars": [
        {
            "model": "",
            "make": "Audi",
            "year": ""
        },
        {
            "model": "A8",
            "make": "",
            "year": "2007"
        }
    ],
    "toys": {
        "color": "Black",
        "type": [
            {
                "brand": "",
                "price": "$100"
            }
        ]
    },
    "id": "xyz",
    "books": [
        {
            "publisher": [
                {
                    "authors": []
                }
            ]
        }
    ],
    "extra": "test"
}

The line:线路:

key = key.replace(/\[\]/g, '.[]').split(".")

is to convert each key to an array, from, for example, the format "cars[].model" to ["cars", "[]", "model"] .是将每个键转换为数组,例如,从格式"cars[].model"["cars", "[]", "model"]

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

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