Pagini recente » Cod sursa (job #574800) | Cod sursa (job #2622595) | Cod sursa (job #2940157) | Cod sursa (job #3270622) | Cod sursa (job #1414705)
#include <cstdio>
#include <string>
using namespace std;
// defines
#define LETTERS_NO 26
// structs
typedef struct _trie_node
{
// constructor
_trie_node()
{
this->words_end_here = 0;
this->words_via_here = 0;
for (int i = 0; i < LETTERS_NO; i++)
{
(this->next)[i] = NULL;
}
}
// fields
int words_end_here;
int words_via_here;
struct _trie_node* next[26];
} trie_node;
// globals
trie_node* root;
// prototypes
void trie_insert(string word);
void trie_erase(string word);
void trie_erase_subtree(trie_node* node);
int trie_number_of_occurrences(string word);
int trie_length_of_longest_prefix(string word);
int main()
{
freopen("trie.in", "r", stdin);
freopen("trie.out", "w", stdout);
root = new trie_node();
int operation_type;
string word;
while (feof(stdin) == false)
{
scanf("%d %s", &operation_type, word);
switch (operation_type)
{
case 0:
trie_insert(word);
break;
case 1:
trie_erase(word);
break;
case 2:
printf("%d\n", trie_number_of_occurrences(word));
break;
case 3:
printf("%d\n", trie_length_of_longest_prefix(word));
break;
default:
break;
}
}
return 0;
}
void trie_insert(string word)
{
trie_node* current = root;
int size = word.size();
for (int i = 0; i < size; i++)
{
current->words_via_here += 1;
int letters_index = word[i] - 'a';
// verify if it does not exist an edge corresponding current's letter
if (current->next[letters_index] == NULL)
{
(current->next)[letters_index] = new trie_node();
}
current = (current->next)[letters_index];
}
current->words_via_here += 1;
current->words_end_here += 1;
}
void trie_erase(string word)
{
trie_node* current = root;
trie_node* ante_current = NULL;
int letters_index;
int size = word.size();
for (int i = 0; i < size; i++)
{
current->words_via_here -= 1;
if (current->words_via_here == 0)
{
trie_erase_subtree(current);
ante_current->next[letters_index] = NULL;
return;
}
letters_index = word[i] - 'a';
if (current->next[letters_index] == NULL)
{
return;
}
ante_current = current;
current = (current->next)[letters_index];
}
current->words_via_here -= 1;
if (current->words_via_here == 0)
{
trie_erase_subtree(current);
ante_current->next[letters_index] = NULL;
return;
}
else
{
current->words_end_here -= 1;
}
}
void trie_erase_subtree(trie_node* node)
{
for (int i = 0; i < LETTERS_NO; i++)
{
if (node->next[i] != NULL)
{
trie_erase_subtree(node->next[i]);
node->next[i] = NULL;
}
}
delete(node);
}
int trie_number_of_occurrences(string word)
{
trie_node* current = root;
int size = word.size();
for (int i = 0; i < size; i++)
{
int letters_index = word[i] - 'a';
// verify if it does not exist an edge corresponding current's letter
if (current->next[letters_index] == NULL)
{
return 0;
}
current = (current->next)[letters_index];
}
return current->words_end_here;
}
int trie_length_of_longest_prefix(string word)
{
trie_node* current = root;
int size = word.size();
int longest_prefix = 0;
for (int i = 0; i < size; i++)
{
int letters_index = word[i] - 'a';
// verify if it does not exist an edge corresponding current's letter
if (current->next[letters_index] == NULL)
{
return longest_prefix;
}
current = (current->next)[letters_index];
longest_prefix += 1;
}
return longest_prefix;
}