嘿,我正试图在我的MERN应用程序中重新排序序列中实现嵌套拖放。我努力为mongodb数据模型找到理想的方法,并为无限子文件夹实现Lexicographic order
或linked lists
。我在这个链接中使用了模型树结构,但是每个节点都有无限的子节点,需要递归和递归函数或柯里化。文档不够清晰,不能这样做。
我想显示所有的树一次,而不是在点击箭头图标后出现。有我的涂鸦的正面一代,只有一个depth
工作,如graph nodes
。也许你有Modified Preorder Tree Traversal
实现的例子。
const tree = data => { // immutable array
let ascendants = data.filter(d=>d.parent==null)
let descandants = data.filter(d=>d.parent)
**strong text**
let form = []
ascendants.map(a=>{
let node1 = {...a}; /// copying
let node1Children = [];
descandants.map(b=>{
let node2 = {...b};
if(node1._id == b.parent){
node1Children.push(node2)
}
})
node1.children = node1Children;
form.push(node1);
})
return form;
}
我不能使用$graphLookup
的结果,因为列表格式不是我想要的。你能给我一些mongodb playground
或分组aggregate
的解决方案吗?下面的json示例显示了我期望的结果。我以前可以这样做,但硬代码是不合适的,而且没有效果。比较是好方法吗?
[
// mongo database
{_id:123, title:'Books', slug:'books', parent:null },
{_id:124, title:'Programming', slug:'programming', parent:null },
{_id:125, title:'JavaScript', slug:'javascript', parent:'programming' },
{_id:126, title:'C++',slug:'cpp', parent:'programming' },
{_id:127, title:'React', slug:'react', parent:'javascript' },
{_id:128, title:'Redux', slug:'redux', parent:'react' },
{_id:129, title:'Toolkit', parent:'redux' },
{_id:130, title:'Saga', parent:'redux' },
{_id:131, title:'Nodejs', parent:'programming' },
{_id:132, title:'Databases', slug:'databases' },
{_id:133, title:'MongoDB', parent:'databases' },
]
[
// what i want
{ title: "Books"},
{ title: "Programming", parent:"computer-science", children: [
{ title: "JavaScript", children: [
{ title: "React", children: [
{ title: "Redux", children: [
{ title: "Saga" },
{ title: "Thunk" },
{ title: "Mobx" },
{ title: "Observable" },
{ title: "Context" },
{ title: "GraphQL" },
{ title: "Toolkit", children:[
{ title: "typescript" },
{ title: "slices", children:[
{ title: "createAsyncThunk" },
{ title: "createSlice" },
] },
] },
] },
{ title: "Nextjs" },
]},
{ title: "Vue", },
{ title: "angular", },
]},
{ title: "C++", },
{ title: "NodeJS", },
] },
{ title: "MongoDB", parent: "databases"},
]
您可以创建一个Map来通过slug
键化您的对象。每个键的值将是父对象的结果对象。包括null
的条目,它将收集顶级元素。
然后再次迭代数据以填充children
数组——如果该属性还不存在,则动态创建它。最后输出顶层元素。
function makeTree(data) {
let children = []; // Top-level elements
let map = new Map(data.map(({title, slug}) => [slug, { title }]))
.set(null, {children});
for (let {slug, parent, title} of data) {
(map.get(parent || null).children ??= [])
.push(slug ? map.get(slug) : {title});
}
return children;
}
// Your mongodb data:
const data = [{_id:123, title:'Books', slug:'books', parent:null },{_id:124, title:'Programming', slug:'programming', parent:null },{_id:125, title:'JavaScript', slug:'javascript', parent:'programming' },{_id:126, title:'C++',slug:'cpp', parent:'programming' },{_id:127, title:'React', slug:'react', parent:'javascript' },{_id:128, title:'Redux', slug:'redux', parent:'react' },{_id:129, title:'Toolkit', parent:'redux' },{_id:130, title:'Saga', parent:'redux' },{_id:131, title:'Nodejs', parent:'programming' },{_id:132, title:'Databases', slug:'databases' },{_id:133, title:'MongoDB', parent:'databases' }];
console.log(makeTree(data));