1

Example:

var someObject = {
'part1' : {
    'name': 'Part 1',
    'txt': 'example',
},
'part2' : {
    'name': 'Part 2',
    'size': '15',
    'qty' : '60'
},
'part3' : [
    {
        'name': 'Part 3A',
        'size': '10',
        'qty' : '20'
    }, {
        'name': '[value]',
        'size': '5',
        'qty' : '20'
    }, {
        'name': 'Part 3C',
        'size': '7.5',
        'qty' : '20'
    }
]};

I need a function to get the path of the object to the value "[value]" which can be anywhere on the object

This object will be passed by the User, for this reason I will not know the structure of it.

something like:

getPath(obj, '[value]');
4
  • 1
    You can only do that by iterating the entire object and looking for the value, and 99% of the time when you need this, you're doing something wrong. Commented Apr 10, 2014 at 18:34
  • Why do you need to know the path? What if [value] exists multiple times and on different paths? Commented Apr 10, 2014 at 18:40
  • classical backtrack algorithm Commented Apr 10, 2014 at 18:49
  • @ExplosionPills each User can have a structure different json, it fills in the settings file path and a model of json, putting [curMusic] on the node where the current music, so I know the json informed where to find the information. It was the easiest way I found to this solution Commented Apr 11, 2014 at 14:51

3 Answers 3

2

Here's some code that should get you a path to your object, not sure how super safe it is:

function getPath(obj, val, path) {
   path = path || "";
   var fullpath = "";
   for (var b in obj) {
      if (obj[b] === val) {
         return (path + "/" + b);
      }
      else if (typeof obj[b] === "object") {
         fullpath = getPath(obj[b], val, path + "/" + b) || fullpath;
      }
   }
   return fullpath;
}

Where testObj is the object in your example:

console.log(getPath(testObj, '20'));      // Prints: /part3/2/qty
console.log(getPath(testObj, "[value]")); // Prints: /part3/1/name
Sign up to request clarification or add additional context in comments.

Comments

0

Try this:

http://jsfiddle.net/n8d2s/1/

The method returns an object, that contains the parts.

function getPath(obj, value, path){
    path = path || [];   
    if(obj instanceof Array || obj instanceof Object){
        //Search within children
        for(var i in obj){
           path.push(i); //push path, will be pop() if no found
            var subPath = getPath(obj[i], value, path);
            //We found nothing in children
            if(subPath instanceof Array){
                if(subPath.length == 1 && subPath[0]==i){
                  path.pop();   
                }
            //We found something in children
            }else if(subPath instanceof Object){
               path = subPath;                
               break;   
            }
        }
    }else{
        //Match ?
        if(obj == value){            
            return {finalPath:path};   
        }else{
            //not ->backtrack
            path.pop();
            return false;   
        }
    } 
    return path;
}

Maybe its not the best code, took me 10min there but it should work.

To see any result, check your dev console F12.

Comments

0

If you try this on the window object you'll end up in trouble as it is self referential. Quick and easy way to get around this is to a depth check:

  function getPath(obj, val, path, depth) {
     if (!depth) depth = 0;
     if (depth > 50) return '';
     path = path || "";
     var fullpath = "";
     for (var b in obj) {
        if (obj[b] === val) {
           return (path + "/" + b);
        }
        else if (typeof obj[b] === "object") {
           fullpath = getPath(obj[b], val, path + "/" + b, depth++) || fullpath;
        }
     }
     return fullpath;
  }

This will return the same kind of path as above:

/part3/2/qty

To make that into an actual reference to variable simply regex:

'window' + '/part3/2/qty'.replace(/\/([0-9]+)\//g, '[$1].').replace(/\//g, '.')

1 Comment

Depth check there because I was trying to write my own, then found yours. Saw it was working on normal objects, just not the window. The window has properties like "parent" which is turtles all the way up!

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.