I’m fairly new to typescript and I have some issues to access an object in array with dynamic depth. For example:
export interface folder{ name: string, type: string, position: number[], // index for each depth level children: folder[]
{ "name": "Folder1", "depth": 0, "position": [0] // indeces for each depth level "children": [ { "name": "Folder2", "depth": 1, "position": [0,0] // indeces for each depth level "children": [ { "name": "Folder3" "depth": 2, "position": [0,0,0] // indeces for each depth level }, { "name": "Folder4" "depth": 2, "position": [0,0,1] // indeces for each depth level } ] } ] }
To get Folder4 I’d use the dot notation like:
this.folder[0].children[0].children[1]
Now I was wondering, if there is a way to dynamicly access the object via the position array without iterating over the whole structure. I managed to get it working by defining a string and adding ".children[PositionIndex]"
for each value in position and executing it with eval
. However that is obviously not a reasonable/safe way to do this.
Any help would be greatly apprecieated.Thanks!
Advertisement
Answer
Instead of having a “position” field that describes the path to a certain depth/folder nested deeply into the structure itself, have a second, shallow structure that maps folder names to depths and use it to reach a folder:
const folders = { "name": "Folder1", "depth": 0, "position": [0], // note: this is wrong, folder one isn't nested and therefor has a position of [] "children": [ { "name": "Folder2", "depth": 1, "position": [0,0], "children": [ { "name": "Folder3", "depth": 2, "position": [0,0,0] }, { "name": "Folder4", "depth": 2, "position": [0,0,1] } ] } ] }; const folderDepths = { // this maps depths to folders. note that "folder1" does not have a // depth, because it is the root node and is not nested. this means // that all nodes nested below folder1 have one path segment less // compared to your original structure. Folder1: [], Folder2: [0], Folder3: [0, 0], Folder4: [0, 1] }; const accessFolder = (name, depths, tree) => { // we use this function to access (sub-)folders. it takes the name // of the folder to reach, the depths-mapping and the original // structure. stops when there are no more children to dig into or // the final depth is reached. returns the accessed (sub-)tree. let retv = tree; let path = depths[name]; for (let i = 0; i < path.length && retv; i += 1) { if (retv.children && retv.children[path[i]]) { retv = retv.children[path[i]]; } } return retv; } console.log(accessFolder('Folder2', folderDepths, folders)); console.log(accessFolder('Folder4', folderDepths, folders));