Business
Jobs
  • About Us
  • Solutions
    • Job Postings
      Post your job and receive qualified candidates in 48h.
    • Candidate Assessments
      500+ technical and psychological tests, plus anti-fraud.
    • Headhunting
      Tailor-made executive search from start to finish.
    • Payroll + EOR
      Payroll dispersal and EOR across 15+ LATAM countries.
  • Pricing
  • Jobs

0

203
Views
Returning value corresponding to a searched key in a deeply nested Javascript object

I have an object like below in Javascript,

const obj = {
      "group1": {
        "sub_group1_1": {
          "inner_sub_group1_1_1": {
            "name": "abc"
          },
          "inner_sub_group1_1_2": {
            "name": "def"
          }
        },
        "sub_group1_2": {
          "inner_sub_group1_2_1": {
            "name": "ghi"
          },
          "inner_sub_group1_2_2": {
            "name": "jkl" 
          }
        }
      },
      "group2": {
        "sub_group2_1": {
          "inner_sub_group2_1_1": {
            "name": "mno"
          },
          "inner_sub_group2_1_2": {
            "name": "pqr"
          }
        },
        "sub_group2_2": {
          "inner_sub_group2_2_1": {
            "name": "stu"
          },
          "inner_sub_group2_2_2": {
            "name": "wxy" 
          }
        }
      }
    }

I want to write a function which could search for a key in the above object and return me the corresponding value of that key, for e.g.,

Input

filterObject(obj, 'inner_sub_group2_2_2')

Output

{
   "name": "wxy
}

Input

filterObject(obj, 'inner_sub_group1_1_1')

Output

{
   "name": "abc
}

Approach

I have written a recursive function for the same, but it doesn't seem to work for the second scenario,

  const filterObject = (obj, searchedKey) => {
    let result = {};
    for (const key in obj) {
      const currentObj = obj[key];
      if (key === searchedKey) {
        result = currentObj;
        break;
      } else if (typeof currentObj === 'object') {
        result = filterObject(currentObj, searchedKey);
      }
    }
    return result;
  };

Any sort of help would be highly appreciated. Thanks!

about 4 years ago · Juan Pablo Isaza
3 answers
Answer question

0

The issue in your code is that if the recursive call is successful, the loop still continues, with another recursive call being made that may not be successful, and so the good result is lost.

You need an if after that recursive call that detects success and breaks out if it is one.

Now, to make the distinction between failure and success you'll make things much easier if you return null when there is no success.

Two lines need to be adjusted:

  const filterObject = (obj, searchedKey) => {
    let result = null; // To indicate nothing found yet
    for (const key in obj) {
      const currentObj = obj[key];
      if (key === searchedKey) {
        result = currentObj;
        break;
      } else if (typeof currentObj === 'object') {
        result = filterObject(currentObj, searchedKey);
        if (result) break; // <--- break out when success!
      }
    }
    return result;
  };

A little improvement might be needed on your is-object test, because typeof null === 'object' is a true expression.

You can use this instead:

if (Object(currentObj) === currentObj)
about 4 years ago · Juan Pablo Isaza Report

0

You need to be able to check whether the recursive call found something, which you aren't doing - right now, you're just reassigning result, and then ignoring it and going on to the next iteration of the loop.

An approach that would work for this particular situation would be to check to see if the resulting object has any keys.

const obj={group1:{sub_group1_1:{inner_sub_group1_1_1:{name:"abc"},inner_sub_group1_1_2:{name:"def"}},sub_group1_2:{inner_sub_group1_2_1:{name:"ghi"},inner_sub_group1_2_2:{name:"jkl"}}},group2:{sub_group2_1:{inner_sub_group2_1_1:{name:"mno"},inner_sub_group2_1_2:{name:"pqr"}},sub_group2_2:{inner_sub_group2_2_1:{name:"stu"},inner_sub_group2_2_2:{name:"wxy"}}}};

const filterObject = (obj, searchedKey) => {
  if (searchedKey in obj) {
    return obj[searchedKey];
  }
  for (const key in obj) {
    const currentObj = obj[key];
    if (typeof currentObj === 'object') {
      const result = filterObject(currentObj, searchedKey);
      if (Object.keys(result).length) return result;
    }
  }
  return {};
};

console.log(filterObject(obj, 'inner_sub_group2_2_2'));
console.log(filterObject(obj, 'inner_sub_group1_1_1'));

But that won't work if the value found isn't an object, or if the found object is empty. (A different object reference unconnected with the original structure would be returned.)

For the more general situation, the recursive call should return two things: whether the nested value was found or not, and the found value (if any). One approach to this is to return an object if something was found, and nothing otherwise.

const obj={group1:{sub_group1_1:{inner_sub_group1_1_1:{name:"abc"},inner_sub_group1_1_2:{name:"def"}},sub_group1_2:{inner_sub_group1_2_1:{name:"ghi"},inner_sub_group1_2_2:{name:"jkl"}}},group2:{sub_group2_1:{inner_sub_group2_1_1:{name:"mno"},inner_sub_group2_1_2:{name:"pqr"}},sub_group2_2:{inner_sub_group2_2_1:{name:"stu"},inner_sub_group2_2_2:{name:"wxy"}}}};

const filterObject = (obj, searchedKey) => {
  if (searchedKey in obj) {
    return { result: obj[searchedKey] };
  }
  for (const key in obj) {
    const currentObj = obj[key];
    if (typeof currentObj === 'object') {
      const result = filterObject(currentObj, searchedKey);
      if (result) return result;
    }
  }
};

console.log(filterObject(obj, 'inner_sub_group2_2_2').result);
console.log(filterObject(obj, 'inner_sub_group1_1_1').result);

about 4 years ago · Juan Pablo Isaza Report

0

Here is a variation of @trincot's and @certainperformance's answers. Nothing fundamentally new, just a slightly different style:

const obj={group1:{sub_group1_1:{inner_sub_group1_1_1:{name:"abc"},inner_sub_group1_1_2:{name:"def"}},sub_group1_2:{inner_sub_group1_2_1:{name:"ghi"},inner_sub_group1_2_2:{name:"jkl",spoiler:null}}},group2:{sub_group2_1:{inner_sub_group2_1_1:{name:"mno"},inner_sub_group2_1_2:{name:"pqr",xtr:false}},sub_group2_2:{inner_sub_group2_2_1:{name:"stu"},inner_sub_group2_2_2:{name:"wxy"}}}};

function deepGet(obj,k,r){ // call with two arguments only
 if(obj&&typeof obj=="object") {
  if(k in obj) return obj[k];
  for(l in obj) if((r=deepGet(obj[l],k))!=null) return r;
 }
 return null;
}

console.log(['inner_sub_group2_2_2','inner_sub_group1_1_1','xtr'].map(k=>deepGet(obj,k)));

about 4 years ago · Juan Pablo Isaza Report
Answer question
Find remote jobs

Discover the new way to find a job!

Top jobs
Top job categories
Business
Post vacancy Pricing Sales
Legal
Terms and conditions Privacy policy
© 2026 PeakU Inc. All Rights Reserved.
Andres GPT
Show me some job opportunities
There's an error!