首页 > 编程语言 >2024华为OD笔试机试 - 模拟目录管理功能 (python/c++/java D卷C卷真题算法)

2024华为OD笔试机试 - 模拟目录管理功能 (python/c++/java D卷C卷真题算法)

时间:2024-08-12 18:27:15浏览次数:9  
标签:abc java python OD mkdir cd current TreeNode 目录

华为OD机试(C卷+D卷)2024真题目录(Java & c++ & python)

题目描述

实现一个模拟目录管理功能的软件,输入一个命令序列,输出最后一条命令运行结果。

支持命令:

  • 创建目录命令:mkdir 目录名称,如 mkdir abc 为在当前目录创建abc目录,如果已存在同名目录则不执行任何操作。此命令无输出。
  • 进入目录命令:cd 目录名称,如 cd abc 为进入abc目录,特别地,cd … 为返回上级目录,如果目录不存在则不执行任何操作。此命令无输出。
  • 查看当前所在路径命令:pwd,输出当前路径字符串。

约束:

  • 目录名称仅支持小写字母;mkdir 和 cd 命令的参数仅支持单个目录,如:mkdir abc 和 cd abc;不支持嵌套路径和绝对路径,如 mkdir abc/efg,cd abc/efg,mkdir /abc/efg,cd /abc/efg 是不支持的。
  • 目录符号为/,根目录/作为初始目录。
  • 任何不符合上述定义的无效命令不做任何处理并且无输出。

输入描述

输入 N 行字符串,每一行字符串是一条命令。

输出描述

输出最后一条命令运行结果字符串。

备注

命令行数限制100行以内,目录名称限制10个字符以内。

用例

输入

mkdir abc
cd abc
pwd

输出

/abc/

说明 在根目录创建一个abc的目录并进入abc目录中查看当前目录路径,输出当前路径/abc/。

解题思路

目录结构,实际就是一颗多叉树。

树节点定义如下:

class TreeNode {

    String dicName; // 当前目录的名字

    TreeNode father; // 当前目录的父目录

    List<TreeNode> children; // 当前目录的子目录

}

树结构:

class Tree {

    TreeNode root; // 树的根目录

    TreeNode cur; // 当前所在目录

}

  • mkdir,其实就是在 tree.cur 目录下创建一个子目录,但是前提是 tree.cur 下面不存在对应子目录名,否则不操作。mkdir操作不改变 tree.cur 指向。

cd,有两种情况:

  • cd … 是返回上级目录(父目录),但是前提是 tree.cur.father 存在,否则不操作。如果 tree.cur.father 存在,则cd … 会改变 tree.cur = tree.cur.father。

  • cd 目录名 是进入子目录,但是前提是 tree.cur 包含对应目录名的子目录,否则不操作。如果 存在对应子目录,则 cd操作会改变 tree.cur = 对应子目录


  • pwd 是输出当前目录的路径字符串,我们可以不停进行 tree.cur = tree.cur.father 的倒序遍历,获取遍历过程中目录名tree.cur.dicName,直到 tree.cur == NULL。最后拼接时注意反转。

C++、Java、Python代码如下:

C++参考代码

#include <bits/stdc++.h>
using namespace std;

struct TreeNode {
public:
    string directoryName;
    TreeNode* parent;
    unordered_map<string, TreeNode*> children;

    TreeNode(string dirName, TreeNode* parent) 
        : directoryName(move(dirName)), parent(parent) {}
};

class FileSystem {
public:
    TreeNode* root;
    TreeNode* current;

    FileSystem() {
        root = new TreeNode("/", nullptr);
        current = root;
    }

    void mkdir(const string& dirName) {
        if (current->children.count(dirName) == 0) {
            current->children[dirName] = new TreeNode(dirName + "/", current);
        }
    }

    void cd(const string& dirName) {
        if (dirName == "..") {
            if (current->parent != nullptr) {
                current = current->parent;
            }
        } else {
            if (current->children.count(dirName) > 0) {
                current = current->children[dirName];
            }
        }
    }

    string pwd() const {
        string path;
        TreeNode* node = current;
        while (node != nullptr) {
            path = node->directoryName + path;
            node = node->parent;
        }
        return path;
    }
};

int main() {
    FileSystem fs;
    string lastOutput = "/";

    do {
        string s;
        getline(cin, s);

        stringstream ss(s);
        string command;
        vector<string> args;

        while (ss >> command) {
            args.push_back(command);
        }

        if (args.empty()) continue;

        const string& cmd = args[0];

        if (cmd == "pwd" && args.size() == 1) {
            lastOutput = fs.pwd();
        } else if ((cmd == "mkdir" || cmd == "cd") && args.size() == 2) {
            const string& dirName = args[1];
            bool isValid = all_of(dirName.begin(), dirName.end(), [](char c) {
                return islower(c);
            });

            if (isValid) {
                if (cmd == "mkdir") {
                    fs.mkdir(dirName);
                } else if (cmd == "cd") {
                    fs.cd(dirName);
                }
            }

            lastOutput = "/";
        }
    } while (!cin.eof());

    cout << lastOutput << endl;

    return 0;
}

Java参考代码

import java.util.HashMap;
import java.util.Scanner;

public class Main {
    static class TreeNode {
        String directoryName;
        TreeNode parent;
        HashMap<String, TreeNode> children;

        public TreeNode(String directoryName, TreeNode parent) {
            this.directoryName = directoryName;
            this.parent = parent;
            this.children = new HashMap<>();
        }
    }

    static class Tree {
        TreeNode root;
        TreeNode current;

        public Tree() {
            // root是根目录,根目录 / 作为初始目录
            this.root = new TreeNode("/", null);
            // current用于指向当前正在操作的目录
            this.current = root;
        }

        public void mkdir(String directoryName) {
            // mkdir 目录名称,如 mkdir abc 为在当前目录创建abc目录,如果已存在同名目录则不执行任何操作
            this.current.children.putIfAbsent(
                directoryName, new TreeNode(directoryName + "/", this.current)); // 目录符号为 /
        }

        public void cd(String directoryName) {
            if (directoryName.equals("..")) {
                // cd .. 为返回上级目录,如果目录不存在则不执行任何操作
                if (this.current.parent != null) {
                    // current 变更指向上级目录
                    this.current = this.current.parent;
                }
            } else {
                // cd 目录名称,如 cd abc 为进入abc目录,如果目录不存在则不执行任何操作
                if (this.current.children.containsKey(directoryName)) {
                    // current 变更指向下级目录
                    this.current = this.current.children.get(directoryName);
                }
            }
        }

        public String pwd() {
            // 输出当前路径字符串
            StringBuilder sb = new StringBuilder();

            // 倒序路径,即不停向上找父目录
            TreeNode current = this.current;
            while (current != null) {
                // 头插目录名,保证路径中目录层级正确
                sb.insert(0, current.directoryName);
                current = current.parent;
            }

            return sb.toString();
        }
    }

    public static void main(String[] args) {
        Scanner sc = new Scanner(System.in);

        // 初始化目录结构
        Tree tree = new Tree();

        // 记录最后一条命令的输出
        String lastCommandOutput = "/";

        outer:
        while (sc.hasNextLine()) {
            String line = sc.nextLine();

            String[] tmp = line.split(" ");

            if (tmp.length == 0) continue;

            String cmdKey = tmp[0];

            if (cmdKey.equals("pwd")) {
                // pwd 命令不需要参数
                if (tmp.length != 1) continue;
                lastCommandOutput = tree.pwd();
            } else if ((cmdKey.equals("mkdir") || cmdKey.equals("cd")) && tmp.length == 2) {
                String directoryName = tmp[1];

                if (!(cmdKey.equals("cd") && directoryName.equals(".."))) {
                    // 目录名约束校验
                    // 目录名称仅支持小写字母
                    for (char c : directoryName.toCharArray()) {
                        if (!Character.isLowerCase(c)) {
                            continue outer;
                        }
                    }
                }

                if (cmdKey.equals("mkdir")) {
                    tree.mkdir(directoryName);
                } else {
                    tree.cd(directoryName);
                }

                lastCommandOutput = "/";
            }
        }

        System.out.println(lastCommandOutput);
    }
}

Python参考代码

class TreeNode:
    def __init__(self, directory_name, parent):
        self.directory_name = directory_name
        self.parent = parent
        self.children = {}

class Tree:
    def __init__(self):
        # root 是根目录,根目录 / 作为初始目录
        self.root = TreeNode("/", None)
        # current 用于指向当前正在操作的目录
        self.current = self.root

    def mkdir(self, directory_name):
        # mkdir 目录名称,如 mkdir abc 为在当前目录创建 abc 目录,如果已存在同名目录则不执行任何操作
        self.current.children.setdefault(directory_name, TreeNode(directory_name + "/", self.current))

    def cd(self, directory_name):
        if directory_name == "..":
            # cd .. 为返回上级目录,如果目录不存在则不执行任何操作
            if self.current.parent is not None:
                # current 变更指向上级目录
                self.current = self.current.parent
        else:
            # cd 目录名称,如 cd abc 为进入 abc 目录,如果目录不存在则不执行任何操作
            if directory_name in self.current.children:
                # current 变更指向下级目录
                self.current = self.current.children[directory_name]

    def pwd(self):
        # 输出当前路径字符串
        path = []
        # 倒序路径,即不停向上找父目录
        node = self.current
        while node:
            path.append(node.directory_name)
            node = node.parent
        # 反转后拼接
        return ''.join(reversed(path))

# 算法逻辑
# 初始化目录结构
tree = Tree()

# 记录最后一条命令的输出
last_command_output = "/"

while True:
    try:
        line = input().strip()
        if not line:
            continue

        tmp = line.split()
        cmd_key = tmp[0]

        if cmd_key == "pwd":
            # pwd 命令不需要参数
            if len(tmp) == 1:
                last_command_output = tree.pwd()
        elif cmd_key in {"mkdir", "cd"} and len(tmp) == 2:
            cmd_val = tmp[1]

            if cmd_val.isalpha() and cmd_val.islower() or (cmd_key == "cd" and cmd_val == ".."):
                if cmd_key == "mkdir":
                    tree.mkdir(cmd_val)
                else:
                    tree.cd(cmd_val)

                # 题目要求输出最后一个命令的运行结果,对于无输出的命令,覆盖前面的命令的输出结果
                last_command_output = "/"
    except EOFError:
        break

print(last_command_output)

标签:abc,java,python,OD,mkdir,cd,current,TreeNode,目录
From: https://blog.csdn.net/hrr397117313/article/details/141128239

相关文章

  • ssm基于java web的商铺租赁管理系统的jsp管理系统|【源码+论文+PPT+部署视频】
    我们提供多元化的技术项目服务,涵盖Java、PHP、Python等编程语言,以及前端开发、人工智能、大数据、单片机开发、ASP.NET、物联网等领域。我们还提供简历模板、面试题库和学习资料,帮助用户提升技术能力和就业竞争力。我们的服务内容包括:免费功能设计、任务书和开题报告撰写、中......
  • AGC182 C - Sum of Number of Divisors of Product
    题目大意:求长度为1,2,...N,的好序列因数个数。好序列满足每个元素\(1\leqx\leqM\)\(N\leq1e18,M\leq16\)很容易想到维护所有好序列质因数的指数+1的乘积。\(\prodb_i,1\leqi\leq6\).考虑每个数对这个乘积的影响。假设我们只有2,3,5这三个质数,序列末端添加15,......
  • 日撸Java三百行(day20:小结)
    目录前言一、面向对象和面向过程相比,有哪些优势?1.封装2.继承3.多态4.协作5.组织结构二、比较顺序表和链表的异同1.相同点2.不同点2.1物理存储结构2.2查找2.3插入和删除三、分析顺序表和链表的优缺点1.顺序表1.1顺序表的优点1.2顺序表的缺点2.链表2.1链表的......
  • Python运行不报错又无任何结果输出
    Python运行不报错又无任何结果输出在Python编程中,遇到程序既不报错也没有任何结果输出的情形,往往让开发者感到困惑。这类问题可能源于多种原因,包括但不限于代码逻辑错误、环境配置问题、或是输入数据的问题。本文将深入探讨这一问题,并提供解决思路、方法、常见场景......
  • JavaScript发展历史
    JavaScript作为一种编程语言,经历了多次发展与演变,以下是其主要历史里程碑:1.诞生与早期发展(1995-1999)1995年:JavaScript由BrendanEich在网景公司(Netscape)发明,最初被称为Mocha,后来改名为LiveScript,最终定名为JavaScript。这种命名是为了利用当时Java语言的流行。199......
  • 掌握JavaScript中的观察者模式:构建响应式编程的基石
    标题:掌握JavaScript中的观察者模式:构建响应式编程的基石在软件开发中,设计模式是解决特定问题的模板。其中,观察者模式是一种非常重要的设计模式,它允许多个对象监听另一个对象的状态变化,并在该对象状态变化时得到通知。这种模式在JavaScript中尤为有用,尤其是在构建响应式应用......
  • 代码质量的守护者:Python静态代码分析工具的集成之道
    标题:代码质量的守护者:Python静态代码分析工具的集成之道在软件开发过程中,代码质量是至关重要的一环。Python作为一种流行的编程语言,拥有众多的静态代码分析工具,它们能够在代码运行之前检测潜在的错误和代码风格问题。本文将深入探讨如何将这些工具集成到Python开发流程中,从......
  • 124. 项目74:简易句子结构分析器——《跟老吕学Python·新手》
    124.项目74:简易句子结构分析器——《跟老吕学Python·新手》124.项目74:简易句子结构分析器124.1目标124.2功能124.3设计124.4实现步骤124.5代码实现124.6测试124.7注意事项124.8小结124.项目74:简易句子结构分析器124.1目标开发一个......
  • 2024年华为OD机试真题-模拟数据序列化传输-Java-OD统一考试(C卷)
    2024年OD统一考试(D卷)完整题库:华为OD机试2024年最新题库(Python、JAVA、C++合集) 题目描述:模拟一套简化的序列化只传输方式,请实现下面的数据编码与解码过程1、编码前数据格式为[位置,类型,值],多个数据的时候用逗号分隔,位置仅支持数字,不考虑重复等场景;类型仅支持:Integer......
  • leetcode递归(LCR 141. 训练计划 III)
    前言经过前期的基础训练以及部分实战练习,粗略掌握了各种题型的解题思路。现阶段开始专项练习。递归大部分题解可以使用迭代方式求解,使用递归是为了熟悉递归的解题思路。描述给定一个头节点为 head 的单链表用于记录一系列核心肌群训练编号,请将该系列训练编号 倒序 记录......