Как найти значение вложенного обьекта

74
08 июня 2021, 05:10

Пытаюсь сделать helper функцию, в которую первым аргументом мы передаём обьект в котором исчем, а вторым это ключ которой должны получить. Проблема в том что не пойму как можно найти вложеный обьект если я захочу написать например c.x

const arr = {
a: 4,
b: 6,
c: { x: 9, y: 8 }
}
const x = keyObjectFinder(this.arr, 'c.x');
console.log('result is ' + x);
helper.js
export function keyObjectFinder(obj, value) {
    if (typeof obj === 'object' && obj.constructor === Object) {
        for (const key in obj) {
            if (obj.hasOwnProperty(key)) {
                let x = obj[value];
                return x;
            }
        }
    }
}
Answer 1

Как вариант

function keyObjectFinder(obj, key) {
    return key.split('.').reduce((subObject, subKey) => {
        if (!subObject || subObject[subKey] === undefined) {
            return undefined;
        }
        return subObject[subKey];
    }, obj);
}
Answer 2

Проблема в том, что строковый ключ объекта может быть абсолютно любым:

{'c.x': 1, c: {x: 2}}  

Поэтому нативный синтаксис не может поддерживать желаемое вами поведение.

Вам необходимо вручную разбивать путь к свойству и итеративно получать доступ ко всё более глубоким значениям:

const obj = { 
  a: 4, 
  b: 6, 
  c: { 
    x: 9, 
    y: 8 
  } 
} 
 
console.log('result is ', traverse(obj, 'c.x')); 
 
 
//////////////////////// 
 
function traverse(obj, path, separator = '.') { 
  const parts = path.split(separator); 
  let res = obj; 
  for (const part of parts) { 
    if (res === undefined) break; 
    res = res[part]; 
  } 
  return res; 
}

Answer 3

А я бы использовал eval, чтобы не изобретать велосипед)

const arr = { 
  a: 4, 
  b: 6, 
  c: { 
    x: 9, 
    y: 8, 
    'key of bubu %$!#$#!!!?': [ 
      15, {moo: 100500} 
    ] 
  } 
}; 
 
const x = keyObjectFinder( arr, `c['key of bubu %$!#$#!!!?'][1].moo`); 
console.log('result is ' + x); 
 
function keyObjectFinder(obj, value) { 
  if (typeof obj === 'object' && obj.constructor === Object) { 
    return eval( 'arr.' + value ); 
  } 
}

Ну и велосипед, без eval:

const arr = { 
  a: 4, 
  b: 6, 
  c: { 
    x: 9, 
    y: 8, 
    'key of bu.bu %$!#$#!!!?': [ 
      15, {moo: 100500} 
    ] 
  } 
}; 
 
const x = keyObjectFinder( arr, "c['key of bu.bu %$!#$#!!!?'][1].moo"); 
console.log('result is ' + x); 
 
function keyObjectFinder(obj, value) { 
  if (typeof obj === 'object' && obj.constructor === Object) { 
    let val = value.match(/^[^.[]+|\[.*?\]|[^.[]+/g); 
    console.log( val ); 
    let x = obj; 
    for( let i = 0; i < val.length; i++ ){ 
      let z = val[i].replace(/\[|\]/g, "").replace(/^['"`]|['"`]$/g,""); 
      x = x[ z ]; 
    } 
    return x; 
  } 
}

READ ALSO
Форматирование текста JS (RegExp)

Форматирование текста JS (RegExp)

Я тут практикуюсь в изучении JavaScript и столкнулся с одной ситуацией: Мне для нормального функционирования нужно число (к примеру 32) перевести...

100
css3 пропорции отображения

css3 пропорции отображения

Почти сделал сайт (http://comp-servby)

100