5-30 目录树 (30分)

题目地址:http://pta.patest.cn/pta/test/15/exam/4/question/857

在ZIP归档文件中,保留着所有压缩文件和目录的相对路径和名称。当使用WinZIP等GUI软件打开ZIP归档文件时,可以从这些信息中重建目录的树状结构。请编写程序实现目录的树状结构的重建工作。

输入格式说明:

输入首先给出正整数N(<=104),表示ZIP归档文件中的文件和目录的数量。随后N行,每行有如下格式的文件或目录的相对路径和名称(每行不超过260个字符):

1) 路径和名称中的字符仅包括英文字母(区分大小写);
2) 符号“\”仅作为路径分隔符出现;
3) 目录以符号“\”结束;
4) 不存在重复的输入项目;
5) 整个输入大小不超过2MB。

输出格式说明:

假设所有的路径都相对于root目录。从root目录开始,在输出时每个目录首先输出自己的名字,然后以字典序输出所有子目录,然后以字典序输出所有文件。注意,在输出时,应根据目录的相对关系使用空格进行缩进,每级目录或文件比上一级多缩进2个空格。

样例输入与输出:

序号 输入 输出
1
7
b
c\
ab\cd
a\bc
ab\d
a\d\a
a\d\z\
root
  a
    d
      z
      a
    bc
  ab
    cd
    d
  c
  b
2
1
z\
root
  z
/* 建立目录树 和 输出 结果均用到了递归的思想 特别要注意数据结构的定义 和 函数参数 这里容易犯错误 */
#include <stdio.h>
#include <iostream> 
#include <stdlib.h>
#include <string>
#include <string.h>
#include <algorithm>
#include <math.h>
#include <map>
#include <unordered_map>
#include <queue>
#include <vector>
#include <iterator>

using namespace std;

#define N 10001

int n;

typedef struct node{
    bool isMuLu;
    string name;
    vector<struct node*> nextJi;
    node(bool _isMulu = true, string _name = "root")
    {
        isMuLu = _isMulu;
        name = _name;
        nextJi.clear();
    }
}Node;

//Node* newNode(bool isMulu,string name1)
//{
// Node* nt = (Node*)malloc(sizeof(Node));
// if (nt != NULL)
// {
// nt->name = name1;
// nt->isMuLu = isMulu;
// nt->nextJi.clear();
// }
// return nt;
//}

Node* root;

Node* createTree(Node* root,string s)
{
    int i;
    if (s.find_first_of('\\') != string::npos) // 有目录
    {
        int pos = s.find_first_of('\\');
        string mut = s.substr(0, pos); // 第一个目录
        string nexts = s.substr(pos+1); // 后面的字符串

        Node* newt = new Node(true, mut);
        int len = root->nextJi.size();
        bool flag = false;

        for (i = 0; i < len; i++)
        {
            Node* nt = root->nextJi.at(i);
            if (nt->name == mut && nt->isMuLu == true)
            {
                if (nexts != ""){
                    //Node* nextt = createTree(root->nextJi.at(i), nexts);
                    //root->nextJi.at(i)->nextJi.push_back(nextt);
                    createTree(root->nextJi.at(i), nexts); // 
                    // 注意是 root->nextJi.at(i) 而不是 自己弄的临时变量 nt 
                }
                flag = true;
                break;
            }
        }
        if (flag == false)
        {
            if (nexts != ""){
                //Node* nextt = createTree(newt, nexts);
                //newt->nextJi.push_back(nextt);
                createTree(newt, nexts); // 上面两句错误 ,只要只一句 就是 newt 递归建立好了
            }
            root->nextJi.push_back(newt);
        }
    }
    else{ // 是个文件
        int len = root->nextJi.size();
        bool flag = false;
        for (i = 0; i < len; i++)
        {
            Node* nt = root->nextJi[i];
            if (nt->name == s && nt->isMuLu == false)
            {
                flag = true;
                break;
            }
        }
        if (flag == false)
        {
            if (s != ""){
                Node* ntt = new Node(false, s);
                root->nextJi.push_back(ntt);
            }
        }
    }
    return root;
}

bool cmp(Node* n1, Node* n2)
{
    if ( (n1->isMuLu && n2->isMuLu) || (!n1->isMuLu&&!n2->isMuLu) )
        return n1->name < n2->name;
    if (n1->isMuLu)
        return true;
    return false;
}

void show(Node* root,int num)
{
    int i;
    for (i = 0; i < 2 * num; i++)
        printf(" ");
    cout << root->name << endl;
    vector<Node*> v = root->nextJi;
    sort(v.begin(), v.end(), cmp);
    int len = v.size();
    for (i = 0; i < len; i++)
    {
        show(v[i], num + 1);
    }
}

int main()
{
    //freopen("in", "r", stdin);
    while (scanf("%d", &n) != EOF)
    {
        root = new Node(true, "root");

        string stmp;
        int i;
        for (i = 0; i < n; i++)
        {
            cin >> stmp;
            root = createTree(root, stmp);
        }
        show(root, 0);
        //printf("\n");
    }
    return 0;
}
#include <cstdio> 
#include <sstream> 
#include <cstring> 
#include <iostream>
#include <string>
#include <vector>
#include <algorithm>
#include <queue>

using namespace std;

#define N 1001

typedef struct node
{
    string name ;
    bool isDir;
    vector<node*> next ;
    node(string _name="")
    {
        name = _name ;
        isDir = true ;
        next.clear() ;
    }
}Fnode;

int n ;

Fnode* createTree(Fnode* root  , string s)
{
    if(s == "")
        return NULL ;
    int pos = s.find_first_of('\\');
    if(pos == string::npos)
    {
        int len = root->next.size() ;
        bool flag = false ;
        for(int i = 0 ; i < len ; i++)
        {
            if( root->next[i]->name == s)
            {
                flag = true ;
                break ;
            }
        }
        if(flag == false)
        {
            Fnode* fn = new node(s);
            fn->isDir = false ;
            root->next.push_back(fn);
        }
    }else{
        int lens = s.size() ;
        string s1 = s.substr(0,pos) ;
        string s2 = s.substr(pos+1,lens-pos) ; 
        bool flag = false ;
        int len = root->next.size() ;
        for(int i = 0 ; i < len ; i++)
        {
            if( root->next[i]->name == s1)
            {
                flag = true ;
                createTree(root->next[i],s2) ;
                break ;
            }
        }
        if(flag == false)
        {
            Fnode* fn = new node(s1) ;
            fn->isDir = true ;
            createTree(fn,s2) ;
            root->next.push_back(fn) ;
        }
    }
}

bool cmp(Fnode* f1 , Fnode* f2)
{
    if(f1->isDir == f2->isDir)
        return f1->name < f2->name;
    if(f1->isDir)
        return true ;
    return false ;
}

void pf(Fnode* root , int ceng)
{
    for(int i= 0 ;i < ceng*2 ;i++)
        printf(" ");
    cout << root->name << endl ;
    int len = root->next.size();
    if(len > 1)
        sort(root->next.begin(),root->next.end() , cmp);
    for(int i= 0 ; i< len ; i++)
    {
        pf(root->next[i] , ceng+1);
    }
}
int main()
{
    //freopen("in.txt", "r", stdin);
    scanf("%d", &n);
    int i ;
    string s ;
    Fnode *root = new node("root") ; 
    for(i = 0 ; i < n ; i++)
    {
        cin >> s ;
        createTree(root , s);
    }
    pf(root,0);
    return 0 ;
}

你可能感兴趣的:(递归,目录树)