Cod sursa(job #2297039)

Utilizator trifangrobertRobert Trifan trifangrobert Data 5 decembrie 2018 10:53:07
Problema Trie Scor 100
Compilator cpp-32 Status done
Runda Arhiva educationala Marime 2.94 kb
#include <fstream>
#include <string>

using namespace std;

const int SIGMA = 26;

class node
{
public:
    int cnt;
    node* v[SIGMA];
    node()
    {
        this->cnt = 0;
        for (int i = 0;i < SIGMA;++i)
            this->v[i] = NULL;
    }
    ~node()
    {
        for (int i = 0;i < SIGMA;++i)
            if (v[i] != NULL)
                delete v[i];
    }
};

class trie
{
public:
    trie()
    {
        root = new node();
    }
    ~trie()
    {
        delete root;
    }
    void AddWord(const string &s)
    {
        RecursiveAdd(root, s, 0);
    }
    void DeleteWord(const string &s)
    {
        RecursiveDelete(root, s, 0);
    }
    int WordCount(const string &s)
    {
        return RecursiveCount(root, s, 0);
    }
    int LongestPrefix(const string &s)
    {
        return RecursivePrefix(root, s, 0);
    }

private:
    node* root;
    void RecursiveAdd(node* currNode, const string &s, int pos)
    {
        if (pos == s.length())
        {
            ++currNode->cnt;
            return;
        }
        if (currNode->v[s[pos] - 'a'] == NULL)
            currNode->v[s[pos] - 'a'] = new node();
        RecursiveAdd(currNode->v[s[pos] - 'a'], s, pos + 1);
    }
    bool CanBeDeleted(node* x)
    {
        if (x->cnt > 0)
            return false;
        bool ok = false;
        for (int i = 0;i < SIGMA;++i)
            ok |= (x->v[i] != NULL);
        return !ok;

    }
    bool RecursiveDelete(node* currNode, const string &s, int pos)
    {
        if (pos == s.length())
        {
            --currNode->cnt;
            return CanBeDeleted(currNode);
        }
        if (RecursiveDelete(currNode->v[s[pos] - 'a'], s, pos + 1))
        {
            delete currNode->v[s[pos] - 'a'];
            currNode->v[s[pos] - 'a'] = NULL;
            return CanBeDeleted(currNode);
        }
        return false;
    }
    int RecursiveCount(node* currNode, const string &s, int pos)
    {
        if (pos == s.length())
            return currNode->cnt;
        if (currNode->v[s[pos] - 'a'] == NULL)
            return 0;
        return RecursiveCount(currNode->v[s[pos] - 'a'], s, pos + 1);
    }
    int RecursivePrefix(node* currNode, const string &s, int pos)
    {
        if (pos == s.length())
            return s.length();
        if (currNode->v[s[pos] - 'a'] == NULL)
            return pos;
        return RecursivePrefix(currNode->v[s[pos] - 'a'], s, pos + 1);
    }
};

int main()
{
    ifstream fin("trie.in");
    ofstream fout("trie.out");
    int op;
    string s;
    trie T;
    while (fin >> op)
    {
        fin >> s;
        if (op == 0)
            T.AddWord(s);
        else if (op == 1)
            T.DeleteWord(s);
        else if (op == 2)
            fout << T.WordCount(s) << "\n";
        else
            fout << T.LongestPrefix(s) << "\n";
    }
    fin.close();
    fout.close();
    return 0;
}