4
let tree = {
    name: "A",
    children: [
        {
            name: 'A-1',
            children: [
                {name: "A-1-A"},
                {name: "A-1-B"},
            ]
        },
        {
            name: 'B-1',
            children: [
                {
                    name: "B-1-A",
                    children: [
                        {name: "B-11-A"},
                        {name: "B-11-B"}
                    ]
                },
                {name: "B-1-B"},
            ]
        },

    ]


};

I am trying to find object from tree object using recursion .

when I call like this searchFn(tree,'A-1') it should return { name: 'A-1', children: [ {name: "A-1-A"}, {name: "A-1-B"}, ] } object

it I call like this searchFn(tree,'A-1-A') it should return this

{name: "A-1-A"}

I tried like this but not working

 function searchFn(obj ,searchText){
        if(obj.name === searchText) return obj
        if(obj.children.length > 0){
          return   searchFn(obj.children.pop(),searchText)
        }
      return null
    }

5 Answers 5

4

You need to iterate the children of the object and take a variable for the result.

function searchFn(object, searchText) {
    var result;
    if (object.name === searchText) return object;
    (object.children || []).some(o => result = searchFn(o, searchText));
    return result || null;
}


let tree = { name: "A", children: [{ name: 'A-1', children: [{ name: "A-1-A" }, { name: "A-1-B" }] }, { name: 'B-1', children: [{ name: "B-1-A", children: [{ name: "B-11-A" }, { name: "B-11-B" }] }, { name: "B-1-B" }] }] };

console.log(searchFn(tree, 'foo'));
console.log(searchFn(tree, 'A-1'));
.as-console-wrapper { max-height: 100% !important; top: 0; }

Sign up to request clarification or add additional context in comments.

Comments

2

First, you should create a class for readability. Then you should have a loop inside the function that iterates over the children and only returns if a child is found.

    class Node {
        static fromStruct = (struct) => {
            const tree = new Node(struct.name);
            if(!struct.children) return tree;
            for(const child of struct.children) {
                tree.children.push(Node.fromStruct(child));
            }
            return tree;
        }

        constructor(name){
            this.name = name;
            this.children = [];
        }
    
        addChild = (parentName, childName) => {
            const parent = this.searchFn(parentName);
            if(!parent) throw new Error("Parent not found");
            parent.children.push(new Node(childName));
        }
    
        searchFn = (name) => {
            if(this.name === name) return this;
            for(const child of this.children) {
                const found = child.searchFn(name);
                if(found !== null) return found;
            }
            return null;
        }
    }


    const data = {
        name: "A",
        children: [
            {
                name: 'A-1',
                children: [
                    {name: "A-1-A"},
                    {name: "A-1-B"},
                ]
            },
            {
                name: 'B-1',
                children: [
                    {
                        name: "B-1-A",
                        children: [
                            {name: "B-11-A"},
                            {name: "B-11-B"}
                        ]
                    },
                    {name: "B-1-B"},
                ]
            },
    
        ]
    };

    const tree = Node.fromStruct(data);
    console.log(tree.searchFn("A-1-A"));

2 Comments

can you please run with sample
@user944513 I improved it a lot
1

const tree = {"name":"A","children":[{"name":"A-1","children":[{"name":"A-1-A"},{"name":"A-1-B"}]},{"name":"B-1","children":[{"name":"B-1-A","children":[{"name":"B-11-A"},{"name":"B-11-B"}]},{"name":"B-1-B"}]}]}

const searchFn = (tree, name) => {
  let result = null;
  if (typeof tree !== "object") return result;
  if (tree.name === name) return tree;
  if (tree.children && tree.children.length) {
    tree.children.some(data => (result = searchFn(data, name)));
  }
  return result;
};
console.log(searchFn(tree, "A-1-A"));
console.log(searchFn(tree, "A-1"));
console.log(searchFn(tree, ""));
.as-console-row {color: blue!important}

Comments

1

You can try something like this

let tree = { name: "A", children: [{ name: 'A-1', children: [{ name: "A-1-A" }, { name: "A-1-B" }] }, { name: 'B-1', children: [{ name: "B-1-A", children: [{ name: "B-11-A" }, { name: "B-11-B" }] }, { name: "B-1-B" }] }] };

function searchFn(obj, text){
  if(obj.name === text) return obj
  else{
    if(obj && obj.children && Array.isArray(obj.children)){
      for(let value of obj.children){
        if(searchFn(value, text)){
          return searchFn(value, text)
        }
      }
    }
  }
  return null
}

console.log(searchFn(tree, 'A-1'))
console.log(searchFn(tree, 'A-1-A'))
console.log(searchFn(tree, 'A-A-A'))

Comments

0

The problem with your function is that it only checks for the popped element from the array in the children property of the passed object, and not the other elements. Try this:

function searchFn(obj ,searchText) { 
    if(obj.name === searchText) return obj; 
    if(obj.children) {
        for (let x of obj.children) {
            let y = searchFn(x,searchText);
            if (y)
                return y;
        }
    }
    return null; 
}

Comments

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.