zoukankan      html  css  js  c++  java
  • Trie树

      借鉴这篇博客,总结了Trie树的相关知识。

    1. 概念

      字典树(Trie)可以保存一些字符串->值的对应关系。基本上,它跟Java的HashMap功能相同,都是key-value映射,只不过Trie的key只能是字符串。Trie来自单词"retrieve,说明它的功能是用于快速地检索。

      的确,Trie的强大之处就在于它的时间复杂度。它的插入和查询时间复杂度都为O(k),其中k为key的长度,与Trie中保存了多少个元素无关。Hash表号称是O(1)的,但在计算hash的时候就肯定会是O(k),而且还有碰撞之类的问题;Trie 的缺点是空间消耗很高。

      其典型的应用是用于统计和排序大量的字符串。

    2. 性质

    Trie树的基本性质可以归纳为:

    • 根节点不包含字符,除根节点意外每个节点只包含一个字符
    • 从根节点到某一个节点,路径上经过的字符连接起来,为该节点对应的字符串
    • 每个节点的所有子节点包含的字符串不相同

      如给出字符串"abc","ab","bd","dda",根据该字符串序列构建一棵Trie树。则构建的树如下:

    image_1bdlnlrapr4l192pm4aengkfam.png-54.3kB

    红色表示可以构成一个单词

    3. 代码实现

    • 构造
        typedef struct Trie_node  
        {  
            int count;                    // 统计单词前缀出现的次数  
            struct Trie_node* next[26];   // 指向各个子树的指针  
            bool exist;                   // 标记该结点处是否构成单词  
        }TrieNode , *Trie;  
    
    • 插入操作
    
        TrieNode* createTrieNode()  
        {  
            TrieNode* node = (TrieNode *)malloc(sizeof(TrieNode));  
            node->count = 0;  
            node->exist = false;  
            memset(node->next , 0 , sizeof(node->next)); //初始化为空指针  
            return node;  
        }  
        void Trie_insert(Trie root, char* word , char* trans)  
        {  
            Trie node = root;  
            char *p = word;  
            int id;  
            while( *p )  
            {  
                id = *p - 'a';  
                if(node->next[id] == NULL)  
                {  
                    node->next[id] = createTrieNode();  
                }  
                node = node->next[id];  // 每插入一步,相当于有一个新串经过,指针向下移动  
                ++p;  
                node->count += 1;      // 这行代码用于统计每个单词前缀出现的次数(也包括统计每个单词出现的次数)  
            }  
            node->exist = true;        // 单词结束的地方标记此处可以构成一个单词  
            strcpy(node->trans , trans);  
        }  
    
    • 查找操作
        int Trie_search(Trie root, char* word)  
        {  
            Trie node = root;  
            char *p = word;  
            int id;  
            while( *p )  
            {  
                id = *p - 'a';  
                node = node->next[id];  
                ++p;  
                if(node == NULL)  
                    return 0;  
            }  
            return node->count;  
        }  
    
  • 相关阅读:
    [整理]正睿 CSP 七连测划水
    关于我想了好久才想出这题咋做这档事
    关于我想了好久才想出这题咋做这档事
    关于我想了好久才想出这题咋做这档事
    [考试总结]ZROI-21-NOIP冲刺-TEST11 总结
    关于我想了很久才想出这题咋做这档事
    [题解]POJ3415 Common Substrings
    [题解]CF1073G Yet Another LCP Problem
    [题解]Codeforces Round #751 (Div. 2) 题解
    [考试总结]ZROI-21-NOIP冲刺-TEST10 总结
  • 原文地址:https://www.cnblogs.com/vachester/p/6709459.html
Copyright © 2011-2022 走看看