Trie

目录

建立Trie树

初始化

插入

询问该字符串出现的次数

求数组中任意两个数异或的最大值

建Trie树

寻找一个数的最大异或值


Trie的作用:高效的存储和查找字符串

建立Trie树

例如:给定若干各字符串,建立一个Trie树。不妨设这个字符串是由小写字母组成的。

初始化

int son[N][26], idx;

ps:son数组表示Trie树的儿子结点,N表示需要建立的字符串的数量,m表示每一个字符串的不同字母。idx表示待使用的son数组下标,从0开始

插入

void insert(char* str)
{
    int p = 0;
    for(int i = 0; str[i]; i++)
    {
        int u = str[i] - 'a';
        if(!son[p][u]) son[p][u] = ++idx;  // 当son数组中没有该字母,那么就开辟一个空间,对应的代码就是++idx
        p = son[p][u];
        // 还可以使用下面代码实现上面代码
        //int& s = son[p][str[i] - 'a'];  s为引用
        //if(!s) s = ++idx;
        //p = s;
    }    
    //cnt[p]++;
}

在每一个字符串结束的后面可以添加一个标记,这个标记可以使用一个cnt数组来表示。
当遍历这个Trie树时,对应下标cnt数组不为空,那么则表示这存在一个字符串

询问该字符串出现的次数

int query(char* str)
{
    int p = 0;
    for(int i = 0; str[i]; i++)
    {
        int u = str[i] - 'a';
        if(!son[p][u]) return 0;
        p = son[p][u];
    }
    return cnt[p];
}

求数组中任意两个数异或的最大值

这个题目可以使用Trie树,根据异或的性质,求一个数和另一个数异或的最大值,要求二进制每一位都不相同。

  1. 先将数组的每一个数以二进制的形式存储到Trie树中
  2. 固定一个数,根据异或要求,寻找Trie树中每一位不相同

建Trie树

void insert(int x)
{
    int p = 0;
    // 根据数的范围2^31,当i = -1时,存储的是-1的补码,1…………111,取反就是0
    for(int i = 30; ~i; i--)
    {
        int s = x >> i & 1;  // s表示x的每一位是0或1
        if(!son[p][s]) son[p][s] = ++idx;  // 当不存在这个数,就开辟新空间,++idx
        p = son[p][s];
        // 当然下面代码和上面是等价的
        //int &s = son[p][x >> i & 1];
        //if(!s) s = ++idx;
        //p = s;
    }
}

寻找一个数的最大异或值

int query(int x)
{
    int p = 0;
    int res = 0;
    for(int i = 30; ~i; i--)
    {
        int s = x >> i & 1;
        if(son[p][!s])  // 根据异或的性质,当s = 0 时,需要寻找1;当s = 1 时,需要寻找0
        {
            // 找到了,那么结果的二进制对应的第i位为1
            res += 1 << i;
            p = son[p][!s];
        }
        else p = son[p][s]; // 没找到,那么结果的二进制对应的第i位为0
    }
    return res;
}

  • 3
    点赞
  • 2
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值