You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何用JavaScript(可使用Underscore)遍历嵌套JSON对象并追踪父子层级

Great question! Traversing deeply nested objects while keeping tabs on your current position in the hierarchy is a super common task—here’s how to pull it off cleanly with vanilla JavaScript or Underscore.js.

First, let’s use your sample object for reference:

const nestedData = {
  'parent1': {
    'name': 'something',
    'children': {
      'name': 'something else'
    }
  },
  'parent2': {
    'name': 'something',
    'children': {
      'name': 'something else',
      'anotherProp': {
        'name': 'whoa..somethin...'
      }
    }
  }
};

Vanilla JavaScript Solution

A recursive function is the most straightforward approach here. We’ll track two key pieces of hierarchy info:

  • currentDepth: A number representing how many levels deep we are (root level = 1)
  • path: An array that builds out the full parent-child chain (e.g., ['parent2', 'children', 'anotherProp'])

Here’s the implementation:

function traverseNestedObj(obj, currentDepth = 1, path = []) {
  // Loop through all keys in the current object
  for (const key of Object.keys(obj)) {
    const value = obj[key];
    // Build the full path to the current key
    const currentPath = [...path, key];
    
    // Example output: log the hierarchy and value
    console.log(`Level: ${currentDepth}, Path: ${currentPath.join(' -> ')}, Value: ${typeof value === 'object' ? '[Object]' : value}`);
    
    // If the value is a non-null object, recurse deeper
    if (typeof value === 'object' && value !== null) {
      traverseNestedObj(value, currentDepth + 1, currentPath);
    }
  }
}

// Run the traversal
traverseNestedObj(nestedData);

When you run this, you’ll get clear output showing exactly where you are in the hierarchy at every step.

Underscore.js Solution

If you’re already using Underscore, you can simplify the loop with _.each and use _.isObject for cleaner type checking:

function traverseWithUnderscore(obj, currentDepth = 1, path = []) {
  _.each(obj, (value, key) => {
    const currentPath = [...path, key];
    
    console.log(`Level: ${currentDepth}, Path: ${currentPath.join(' -> ')}, Value: ${_.isObject(value) ? '[Object]' : value}`);
    
    // Recurse only if the value is a valid non-null object
    if (_.isObject(value) && value !== null) {
      traverseWithUnderscore(value, currentDepth + 1, currentPath);
    }
  });
}

// Run the traversal
traverseWithUnderscore(nestedData);

Handling Edge Cases

If your object might have circular references (an object that references itself somewhere in the hierarchy), you’ll need to add a check to avoid infinite recursion. We can use a WeakSet to track visited objects:

function traverseWithCircularCheck(obj, currentDepth = 1, path = [], visited = new WeakSet()) {
  // Skip if we've already processed this object
  if (visited.has(obj)) return;
  visited.add(obj);

  for (const key of Object.keys(obj)) {
    const value = obj[key];
    const currentPath = [...path, key];
    
    console.log(`Level: ${currentDepth}, Path: ${currentPath.join(' -> ')}, Value: ${typeof value === 'object' ? '[Object]' : value}`);
    
    if (typeof value === 'object' && value !== null) {
      traverseWithCircularCheck(value, currentDepth + 1, currentPath, visited);
    }
  }
}

This way, you’ll never hit a stack overflow from circular references.

You can tweak the logging/processing logic to fit your needs—whether you’re collecting data from a specific level, modifying properties, or just auditing the structure.

内容的提问来源于stack exchange,提问作者Steve Rogers

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.05.26 09:51:05