Geoff
Geoff

Reputation: 6649

Javascript use find in nested arrays

I have the following array data

var data = [
    {name:'hr', to:'/hr/settings', children:[
        {name:'Language', to:'/hr/settings/general/languages', icon:''},
        {name:'Marital Status', to:'/hr/settings/general/marital-status', icon:''},
        {name:'Nationalities', to:'/hr/settings/general/nationalities', icon:''},
        {name:'Ethnicities', to:'/hr/settings/general/ethnicities', icon:''},
        {name:'Religions', to:'/hr/settings/general/religions', icon:''},
        {name:'Tribes', to:'/hr/settings/general/tribes', icon:''},
        {name:'Relations', to:'/hr/settings/general/relations', icon:''}
    ]},
    {name:'education', to:'/hr/education', children:[
        {name:'Universities',to:'/hr/settings/education/universities', icon:''},
        {name:'Relations',to:'//hr/settings/education/relations', icon:''}
    ]}
];

So what am looking forward to do is find the index of the data array which has to value in it or its children similar to a certain string

so i have the following

function getArrayIndex(tovalue) {
    const pathnavigated = data.find(link => link.to === tovalue);
    return data.indexOf(pathnavigated);
}

The above works for the array eg getArrayIndex('/hr/settings') but now i want it to search also the children

eg

getArrayIndex('/hr/settings/general/marital-status') 

should return the first index

and getArrayIndex('/hr/settings/education/universities') should return the second index

How do i make the function to search even the children and return the value of the index on the parent array (of the child)

Upvotes: 0

Views: 57

Answers (3)

nikksan
nikksan

Reputation: 3481

Somebody already beat me to it.. but still..

function getIndex(array, search) {
    for (let i = 0;i < array.length; i++) {
        if (array[i].to === search) {
            return i;
        }

        if (Array.isArray(array[i].children)) {
            for (let j = 0; j < array[i].children.length; j++) {
                if (array[i].children[j].to === search) {
                    return j;
                }
            }
        }
    }

    return -1;
}

Upvotes: 1

Emaro
Emaro

Reputation: 1497

I'd use some() instead of filter(), so you don't have to check the length. Some returns true if any of the childern passes the check in the lambda. If you still want to search the top level items, don't forget to check for both conditions: link.to === tovalue || link.children.some(c => c.to === tovalue).

function getArrayIndex(tovalue) {
    const pathnavigated = data.find(link =>
        link.to === tovalue || link.children.some(c => c.to === tovalue));
    return data.indexOf(pathnavigated);
}

Upvotes: 2

I just did a slight modification to your function getArrayIndex and added the following:

data.find(link => link.children.filter(b=>b.to == tovalue).length > 0)

In here, I filter the children and if there is at least one children that match your string, returns it.

var data = [
      {name:'hr',to:'/hr/settings', children:[
                    {name:'Language',to:'/hr/settings/general/languages', icon:''},
                    {name:'Marital Status',to:'/hr/settings/general/marital-status', icon:''},
                    {name:'Nationalities',to:'/hr/settings/general/nationalities', icon:''},
                    {name:'Ethnicities',to:'/hr/settings/general/ethnicities', icon:''},
                    {name:'Religions',to:'/hr/settings/general/religions', icon:''},
                    {name:'Tribes',to:'/hr/settings/general/tribes', icon:''},
                    {name:'Relations',to:'/hr/settings/general/relations', icon:''}]},   
       {name:'education', to:'/hr/education', children:[
                    {name:'Universities',to:'/hr/settings/education/universities', icon:''},
                    {name:'Relations',to:'//hr/settings/education/relations', icon:''}]}

  ]
  
 function getArrayIndex(tovalue){
    const pathnavigated = data.find(link => link.children.filter(b=>b.to == tovalue).length > 0);
    return data.indexOf(pathnavigated);
}

console.log(getArrayIndex('/hr/settings/education/universities') )

Upvotes: 2

Related Questions