树结构未按预期构建

我正在尝试编写一个从给定起始目录创建树的函数。换句话说,我选择一个目录,然后该函数将绝对映射该特定目录中的所有内容。我以前从未做过这样的事情,但是我已经接近预期的输出。但是,我不确定我要去哪里哪里。

起始目录

> Test Root
    > 1a
    > 1b
        > 2a
        > 2b
        > 2c
    > 1c
        > 2a
    > 1d
        > 2a
        > 2b
    > testfile.txt

输出

第一个级别不错。第二层几乎不错,但是由于某种原因,它正在复制parent属性并创建另一个嵌套对象。它还总是插入type属性。我曾尝试删除constructor中的属性,但输出结果令人困惑。

{
  "parent": null,"path": "C:\\Users\\Anthony\\Desktop\\Test Root","name": "Test Root","kids": [
    {
      "parent": {
        "parent": "C:\\Users\\Anthony\\Desktop\\Test Root","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1a","name": "1a","kids": []
      },"type": "fileType"
    },{
      "parent": {
        "parent": "C:\\Users\\Anthony\\Desktop\\Test Root","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1b","name": "1b","kids": [
          {
            "parent": {
              "parent": "C:\\Users\\Anthony\\Desktop\\Test Root\\1b","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1b\\2a","name": "2a","kids": []
            },"type": "fileType"
          },{
            "parent": {
              "parent": "C:\\Users\\Anthony\\Desktop\\Test Root\\1b","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1b\\2b","name": "2b","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1b\\2c","name": "2c","type": "fileType"
          }
        ]
      },"path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1c","name": "1c","kids": [
          {
            "parent": {
              "parent": "C:\\Users\\Anthony\\Desktop\\Test Root\\1c","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1c\\2a","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1d","name": "1d","kids": [
          {
            "parent": {
              "parent": "C:\\Users\\Anthony\\Desktop\\Test Root\\1d","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1d\\2a",{
            "parent": {
              "parent": "C:\\Users\\Anthony\\Desktop\\Test Root\\1d","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\1d\\2b","path": "C:\\Users\\Anthony\\Desktop\\Test Root\\testfile.txt","name": "testfile.txt","type": "fileType"
      },"type": "fileType"
    }
  ]
}

功能

async function createTree(root){
  const
    Node = class {
      constructor(parent,path,name,fifo){
        this.parent = parent
        this.path = path
        this.name = name
        fifo ? this.kids = [] : this.type = 'fileType'
      }
      addChild(parent,fifo){
        this.kids.push(new Node(parent,fifo))
      }
    },traverse = async function(node,path){
      const childPaths = await fsp.readdir(path)
      for (const childPath of childPaths){
        const
          name = childPath,stats = await fsp.stat(join(path,childPath))
        let
          fifo

        if (stats.isDirectory()) fifo = 1
        else if (stats.isFile()) fifo = 0

        const
          childNode = new Node(path,join(path,childPath),fifo)

        node.addChild(childNode)

        traverse(childNode,childPath))
      }
    },rootName = root.slice(-1) === '\\' ? root.slice(0,1) : root.slice(root.lastIndexOf('\\')+1),tree = new Node(null,root,rootName,1)

    traverse(tree,root)

    setTimeout(function(){
      console.log(JSON.stringify(tree,null,2))
    },2500)
}

我刚刚意识到我的异步函数没有返回任何东西。明天我将不得不审视所有这一切。

j445566321 回答:树结构未按预期构建

问题是您在这里仅将第一个参数传递给addChild函数。

addChild函数期望提供4个参数。但是:

node.addChild(childNode)

// is approximately equivalent to:

addChild ( Node {...},undefined,undefined)

您应该像这样调用函数:

node.addChild(childNode.path,childNode.path,childNode.name,childNode.fifo)

您在逻辑上走上了正确的道路,正在寻求一个很好的递归解决方案,但我认为该类有点过分适用,并且对于诸如此类的功能问题而言,也太面向对象了。这是功能更强的版本的简要示例,应该可以为您带来预期的结果:

const nodePath = require('path');
const fs = require('fs');

/**
 * Supply an `fs` function and it will turn it into a promisified version
 * @param {Function} fn The function to promisify. This means you do not 
 * need the `fsp` library.
 */
function promisify (fn) {
  return (...args) => new Promise((resolve,reject) => fn(...args,(err,data) => err ? reject(err) : resolve(data)));
};

// Create promisified versions of `fs.stat` and `fs.readdir`
const stat = promisify(fs.stat);
const readdir = promisify(fs.readdir);

function createDirectory (parent,path,name,kids) {
  return { parent,kids: kids || [] };
};

function createFile (parent,name) {
  return { parent,type: 'fileType' };
}

// The main recursive function.
async function createTree (parent,path) {
  let stats = await stat(path);

  if (stats.isDirectory()) {
    const children = await readdir(path);

    // Because each recursive call retruns a promise,we want to continue only when
    // all of them have resolved. So we use Promise.all for this.
    let child_nodes = await Promise.all(
      children.map(child => createTree(path,nodePath.join(path,child)))
    );

    // Create a directory node
    return createDirectory(parent,nodePath.basename(path),child_nodes);
  }

  // Create a file node
  return createFile(parent,nodePath.basename(path));
};


// Startup code,can use your own stuff here.
async function start () {
  let tree = await createTree(null,'/home/james/stackoverflow/58706769/Test Root');

  console.log(JSON.stringify(tree,null,2));
}

start();

在Node中运行此文件,我得到以下输出:

{
  "parent": null,"path": "/home/james/stackoverflow/58706769/Test Root","name": "Test Root","kids": [
    {
      "parent": "/home/james/stackoverflow/58706769/Test Root","path": "/home/james/stackoverflow/58706769/Test Root/1a","name": "1a","kids": []
    },{
      "parent": "/home/james/stackoverflow/58706769/Test Root","path": "/home/james/stackoverflow/58706769/Test Root/1b","name": "1b","kids": [
        {
          "parent": "/home/james/stackoverflow/58706769/Test Root/1b","path": "/home/james/stackoverflow/58706769/Test Root/1b/2a","name": "2a","kids": []
        },{
          "parent": "/home/james/stackoverflow/58706769/Test Root/1b","path": "/home/james/stackoverflow/58706769/Test Root/1b/2b","name": "2b","path": "/home/james/stackoverflow/58706769/Test Root/1b/2c","name": "2c","kids": []
        }
      ]
    },"path": "/home/james/stackoverflow/58706769/Test Root/1c","name": "1c","kids": [
        {
          "parent": "/home/james/stackoverflow/58706769/Test Root/1c","path": "/home/james/stackoverflow/58706769/Test Root/1c/2a","path": "/home/james/stackoverflow/58706769/Test Root/1d","name": "1d","kids": [
        {
          "parent": "/home/james/stackoverflow/58706769/Test Root/1d","path": "/home/james/stackoverflow/58706769/Test Root/1d/2a",{
          "parent": "/home/james/stackoverflow/58706769/Test Root/1d","path": "/home/james/stackoverflow/58706769/Test Root/1d/2b","path": "/home/james/stackoverflow/58706769/Test Root/testfile.txt","name": "testfile.txt","type": "fileType"
    }
  ]
}
本文链接:https://www.f2er.com/3161423.html

大家都在问