展平路线树

时间:2019-03-13 16:05:58

标签: javascript recursion tree

我正在尝试找到一种使用路由(香草js)和子路由展平阵列的方法,以便获得具有相同级别的对象但它们的name和{ {1}}属性基于其“级别”。

例如,我希望path成为name之类的东西,dashboard.settings.user.......也会将“有效”路径的路径连接在一起。

我一直在尝试使用递归函数,但无法弄清楚如何跟踪级别。

更新:

path

更新2:

基于Nina解决方案,我要求一种保留原始对象/值的方法,但是将var routesConfig = [ { name: 'dashboard', path: '/dashboard', children: [ { name: 'settings', path: '/settings', children: [ { name: 'user', path: '/user' }, { name: 'email', path: '/email', children: [ { name: 'template', path: '/template', children: [ { name: 'error', path: '/error' }, { name: 'success', path: '/success' } ], name: 'lists', path: '/lists', children: [ { name: 'signup', path: '/signup' }, { name: 'newsletter', path: '/newsletter' } ] }, { name: 'sender', path: '/sender' } ] } ] }, { name: 'contact', path: '/contact', children: [ { name: 'person', path: '/person', children: [ { name: 'john', path: '/john' }, { name: 'jane', path: '/jane' } ] } ] } ] }, ] flattenRoutes(); function flattenRoutes(){ let routes = []; routesConfig.map(route => { const {name, path, children} = route; routes.push({name, path}); if(children && children.length){ iterateRouteChildren(route, routes, 1, []); } }); console.log("routes", routes); } function iterateRouteChildren(parent, routes, depth, tree){ for(let i = 0; i < parent.children.length; i++){ let childRoute = parent.children[i]; let name = childRoute.name; let path = childRoute.path; if(depth === 1){ tree = []; }else{ tree.push(childRoute.name) } routes.push({name, path, tree: tree.filter(Boolean).join('.')}); if(childRoute.children && childRoute.children.length){ iterateRouteChildren(childRoute, routes, depth + 1, tree); } } } name重写为它们的“新”值,例如应该路由“ email”将其path读为:name,并将其dashboard.settings.email重写为:path 因此,请对每个对象进行突变,并保留其不变的属性(但仍将其保留为一个平面数组,因此不要嵌套子数组)。

更新3:

尝试澄清。我嵌套的routesConfig将包含具有“名称”,“路径”,“其他属性”和也许“子代”之类的属性的对象。

我想弄平整棵树,所以一切都在同一水平上,但是所有子项都应根据其深浅程度来重写其“名称”和“路径”。示例:

/dashboard/settings/email

谢谢

1 个答案:

答案 0 :(得分:0)

您可以通过将最后的namepath移交给嵌套对象来采取迭代和递归的方法。

function getFlat(array, n = '', p = '') {
    return array.reduce((r, { children = [], ...o }) => {
        var name = n + (n && '.') + o.name,
            path = p + o.path;
        return r.concat(Object.assign({}, o, { name, path }), getFlat(children, name, path));
    }, []);
}

var routes = [{ name: 'dashboard', path: '/dashboard', children: [{ name: 'settings', path: '/settings', children: [{ name: 'user', path: '/user' }, { name: 'email', path: '/email', children: [{ name: 'template', path: '/template', children: [{ name: 'error', path: '/error' }, { name: 'success', path: '/success' }] }, { name: 'lists', path: '/lists', children: [{ name: 'signup', path: '/signup' }, { name: 'newsletter', path: '/newsletter' }] }, { name: 'sender', path: '/sender' }] }] }, { name: 'contact', path: '/contact', children: [{ name: 'person', path: '/person', children: [{ name: 'john', path: '/john' }, { name: 'jane', path: '/jane' }] }] }] }],
    flat = getFlat(routes);

console.log(flat);
.as-console-wrapper { max-height: 100% !important; top: 0; }