编辑代码

// 设置标准输入接口
const rl = require("readline").createInterface({ input: process.stdin });
var iter = rl[Symbol.asyncIterator]();
const readline = async () => (await iter.next()).value;

// 问题描述:计算文件系统中指定目录的总大小
// 输入格式:第一行两个整数 m n,m表示文件/目录总数,n表示要计算大小的目录ID
// 后面m行,每行包含:id size children
// - id: 文件/目录的唯一标识符
// - size: 文件/目录自身的大小
// - children: 子文件/目录的ID列表,格式为(id1,id2,...),空表示没有子节点

void (async function () {
  // 读取文件/目录总数m和目标目录ID n
  const [m, n] = (await readline()).split(" ").map(Number);

  // 存储所有文件/目录信息的数组
  const files = [];

  // 读取每个文件/目录的信息
  for (let i = 0; i < m; i++) {
    // 解析每行输入的三个部分:id、size和children
    let [id, size, child] = (await readline()).split(" ");

    // 处理children部分,提取括号中的内容
    // 使用正则表达式分割并过滤掉空字符串
    child = child.split(/[()]/).filter((item) => item != "")[0];

    // 如果存在子节点,将其转换为数字数组
    if (child) {
      child = child.split(",").map(Number);
      files.push({ id: Number(id), size: Number(size), child });
    } else {
      // 如果没有子节点,设置为空数组
      files.push({ id: Number(id), size: Number(size), child: [] });
    }
  }

  // 找到目标目录节点
  let root = files.find((item) => item.id == n);

  // 递归计算目录大小的函数
  const getSize = (root) => {
    // 基础情况:如果节点不存在,返回0
    if (!root) return 0;

    // 获取当前节点的大小
    let val = root.size;

    // 递归计算所有子节点的大小并累加
    for (const child of root.child) {
      val += getSize(files.find((item) => item.id == child));
    }
    return val;
  };

  // 输出目标目录的总大小
  console.log(getSize(root));
})();

// 示例说明:
// 输入:
// 4 1        // 4个文件/目录,计算ID为1的目录大小
// 1 2 (2,3)  // ID=1,大小=2,包含子节点2和3
// 2 3 (4)    // ID=2,大小=3,包含子节点4
// 3 1 ()     // ID=3,大小=1,没有子节点
// 4 4 ()     // ID=4,大小=4,没有子节点
// 输出:10   // ID=1的目录总大小 = 2 + 3 + 1 + 4 = 10