Cod sursa(job #943475)

Utilizator BitOneSAlexandru BitOne Data 25 aprilie 2013 16:39:41
Problema Trie Scor 100
Compilator cpp Status done
Runda Arhiva educationala Marime 3.13 kb
#include <string>
#include <fstream>
#include <cstdlib>

using namespace std;

const int RADIX = 27;

class Trie
{
protected :
    struct _Trie_Node
    {
        int countSons;
        int countApp;
        _Trie_Node *link[RADIX];

        _Trie_Node() : countSons(0), countApp(0)
        {
            for(int i = 0; i < RADIX; ++i)
                link[i] = NULL;
        }
    };
    typedef _Trie_Node *_PTrie_Node;

private :
    _PTrie_Node root;

    void add(_PTrie_Node& root, string::const_iterator it, string::const_iterator iend)
    {
        if(NULL == root)
        {
            root = new _Trie_Node();
        }
        if(it >= iend) //it is the end
        {
            root->countApp += 1;
            return;
        }
        if(NULL == root->link[*it - 'a'])
        {
            ++root->countSons;
        }
     //   char x = *it;
        add(root->link[*it - 'a'], it + 1, iend);
    }

    bool deleteWord(_PTrie_Node& root, string::const_iterator it, string::const_iterator iend)
    {
        if(NULL == root) return false;
        if(it >= iend)
        {
            --root->countApp;
            return 0 == root->countApp && 0 == root->countSons;
        }
       // char x = *it;
        if(true == deleteWord(root->link[*it - 'a'], it + 1, iend))
        {
            --root->countSons;
            delete root->link[*it - 'a'];
            root->link[*it - 'a'] = NULL;
        }
        return 0 == root->countApp && 0 == root->countSons;
    }

    int countApp(const _PTrie_Node& root, string::const_iterator it, string::const_iterator iend)
    {
        if(NULL == root) return 0;
        if(it >= iend) return root->countApp;
        return countApp(root->link[*it - 'a'], it + 1, iend);
    }

    int longestPrefix(const _PTrie_Node& root, string::const_iterator it, string::const_iterator iend)
    {
        if(NULL == root || NULL == root->link[*it - 'a'] || it >= iend) return 0;
        return longestPrefix(root->link[*it - 'a'], it + 1, iend) + 1;
    }

public :
    Trie() : root(NULL)
    {

    }

    void add(const string& x)
    {
        if(x.empty()) return;
        add(root, x.begin(), x.end());
    }

    int countApp(const string& x)
    {
       if(x.empty()) return 0;
       return countApp(root, x.begin(), x.end());
    }

    int longestPrefix(const string& x)
    {
        if(x.empty()) return 0;
        return longestPrefix(root, x.begin(), x.end());
    }

    bool deleteWord(const string& x)
    {
        if(x.empty()) return false;
        return deleteWord(root, x.begin(), x.end());
    }

};

int main()
{
    int op;
    Trie root;
    string word;
    ifstream in("trie.in");
    ofstream out("trie.out");

    while(in >> op >> word)
    {
        switch(op)
        {
            case 0 : root.add(word); break;
            case 1 : root.deleteWord(word); break;
            case 2 : out << root.countApp(word) << '\n'; break;
            case 3 : out << root.longestPrefix(word) << '\n'; break;
            default : return EXIT_FAILURE;
        }
    }
    return EXIT_SUCCESS;
}