Javascript: хранение ключа / значения в объекте с многоуровневой вложенностью - PullRequest
0 голосов
/ 24 апреля 2020

Мне дали два массива: -

var keys = ['a.b', 'a.c.d', 'a.e', 'h[0]'];
var values = [10, 20, {}, 40];

Вывод, который я хочу получить: -

{
    a: { 
         b: 10, 
         c: {
            d: 20
         }, 
         e: {}
    },
    h: [40]
}

То, что я до сих пор пробовал, это

let constructObject = (keys, values) => {
    let output = {};
    for(let i = 0; i<keys.length; i++) {
        let props = keys[i].split('.');
        for(let j=0; j<props.length;j++) {
            if(props.length > (j+ 1)) {
                if(output[props[j]] == undefined) {
                  output[props[j]] = {};
                }
            } else {
              output[props[j]] = values[i];
            }
        }
    }
    return output;
}

Приведенный выше код не является вложенным глубже. Я пытался сохранить вложенный ключ уровня, также используя для l oop, но не смог получить какой-либо способ хранения ключей, так как javascript дает только способ сохранить значение, а не вложенные ключи уровня.

1 Ответ

1 голос
/ 24 апреля 2020

Вы можете разделить дорожки на более мелкие части, такие как свойства и индексы, и построить новый объект, соблюдая следующий ключ и решить, нужно ли брать массив или объект.

function setValue(target, keys, value) {
    const
        isWrapped = s => s.startsWith('[') && s.endsWith(']'),
        unwrap = s => isWrapped(s) ? s.slice(1, -1) : s,
        path = keys.match(/\[[^\]+]\]|[^\.\[\]]+/g),
        last = path.pop();

    path
        .reduce((o, k, i, { [i + 1]: next = last }) =>
            o[unwrap(k)] = o[unwrap(k)] || (isWrapped(next) ? [] : {}), target)
        [unwrap(last)] = value;
}

var keys = ['a.b', 'a.c.d', 'a.e', 'h[0]'],
    values = [10, 20, {}, 40],
    i,
    l = keys.length,
    result = {};

for (i = 0; i < l; i++) setValue(result, keys[i], values[i]);

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