Trie可持久化Trie

WARNING:以下代码未经测试,若发现错误,欢迎指出qwq~

Trie树(字典树)

一种简单的数据结构,可存储大量字符串,可在$O(len)$的时间内完成插入,删除,查找等操作。

下面是一个简单的例子,对于abc,abd,abcd,bcd这四个字符串建Trie树,如下图:

其中,红色节点为一个字符串的结尾。对于任意节点,从根节点到该节点路径上字符组成的字符串即为该节点表示的字符串。

基本操作

相关变量

1 int root,cnt,ch[1000010][26],son[1000010];
2 bool flag[1000010];
3 void init(){
4     memset(flag,false,sizeof(flag));
5     memset(son,0,sizeof(son));
6     memset(ch,0,sizeof(ch));
7     root=cnt=1;
8     return;
9 }

root即为根节点,cnt用于动态建树,ch[i][j]表示i节点的第j个子节点(表示字符char('a'+i))的编号,son[i]表示i节点的子节点数,flag[i]表示i节点是否为某个字符串的末尾。

插入

 1 void ins(int rt,int dep){
 2     if(dep==len){
 3         flag[rt]=true;
 4         return;
 5     }
 6     if(!ch[rt][s[dep]-'a']){
 7         ch[rt][s[dep]-'a']=++cnt;
 8         son[rt]++;
 9     }
10     ins(ch[rt][s[dep]-'a'],dep+1);
11     return;
12 }

删除

 1 bool del(int rt,int dep){
 2     if(dep==len){
 3         if(flag[rt]){
 4             flag[rt]=false;
 5             return true;
 6         }
 7         return false;
 8     }
 9     if(!ch[rt][s[dep]-'a'])
10         return false;
11     if(del(ch[rt][s[dep]-'a'],dep+1)){
12         if(!son[ch[rt][s[dep]-'a']]&&!flag[ch[rt][s[dep]-'a']]){
13             ch[rt][s[dep]-'a']=0;
14             son[rt]--;
15         }
16         return true;
17     }
18     return false;
19 }

查找

1 bool query(int rt,int dep){
2     if(dep==len)
3         return flag[rt];
4     if(!ch[rt][s[dep]-'a'])
5         return false;
6     return query(ch[rt][s[dep]-'a'],dep+1);
7 }

以上三个是Trie树的基本操作,下面来讲一下Trie树的其它运用。

拓展运用

求第k小字符串

存储以每个节点为根的子树中的末尾节点个数(size[i])即可。

 1 void kth(int rt,int dep,int k){
 2     if(k>size[rt]){
 3         puts("have no kth string");
 4         return;
 5     }
 6     for(int i=0;i<26;i++)
 7         if(k>size[ch[rt][i]])
 8             k-=size[ch[rt][i]];
 9         else if(ch[rt][i]){
10             putchar('a'+i);
11             kth(ch[rt][i],dep+1,k);
12         }
13     return;
14 }

长公共前缀

用LCA求两个字符串对应的末尾节点的最近公共祖先即可,时间复杂度O(log2n)。

 1 代码不贴了,懒~~~ 

最大异或值

将每个数转化为二进制,添加前缀0至相同位数,然后从最高位开始插入。查询时从最高位开始查询是否有与相应位置异或值为1的节点即可。

 1 太水了,也不贴代码了~~~ 

可持久化Trie树

在做题过程中,我们常常会遇到求区间第k大字符串,区间与某数异或最大值之内的问题,我们便可以采用可持久化Trie树来解决这类问题。

依旧以abc,abd,abcd,bcd这四个字符串为例建可持久化Trie,如下图:

红色节点意义同上。

基本操作

相关变量

 1 int cnt=0,root[1000010],size[1000010],ch[1000010][26];
 2 bool flag[1000010];
 3 void init(){
 4     memset(flag,false,sizeof(flag));
 5     memset(root,0,sizeof(root));
 6     memset(size,0,sizeof(size));
 7     memset(ch,0,sizeof(ch));
 8     cnt=0;
 9     return;
10 }

意义同上。

插入

 1 void ins(int &now,int last,int dep){
 2     if(!now)
 3         now=++cnt;
 4     if(dep==len){
 5         flag[now]=true;
 6         size[now]=size[last]+1;
 7         return;
 8     }
 9     int sign=s[dep]-'a';
10     for(int i=0;i<26;i++)
11         if(i!=sign){
12             ch[now][i]=ch[last][i];
13             size[now]+=size[ch[last][i]];
14         }
15     ins(ch[now][sign],ch[last][sign],dep+1);
16     size[now]+=size[ch[now][sign]];
17     return;
18 }

区间第k小查询

 1 void kth(int rl,int rr,int dep,int k){
 2     if(k>size[rr]-size[rl]){
 3         puts("have no kth string");
 4         return;
 5     }
 6     for(int i=0;i<26;i++)
 7         if(k>size[ch[rr][i]]-size[ch[rl][i]])
 8             k-=size[ch[rr][i]]-size[ch[rl][i]];
 9         else if(size[ch[rr][i]]-size[ch[rl][i]]>0){
10             putchar('a'+i);
11             kth(ch[rl][i],ch[rr][i],dep+1,k);
12             return;
13         }
14     return;
15 }

区间最大异或值

 1 好吧,还是懒得打~~~ 

转载于:https://www.cnblogs.com/gzez181027/p/Trie.html

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/485366.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

视觉的目的是什么?从监督学习到对比学习,回顾CV发展史

来源&#xff1a;AI科技评论作者&#xff1a; 周纵苇知乎摘要&#xff1a;视觉&#xff0c;对于人类或动物来说&#xff0c;似乎是一件稀松平常的事情&#xff0c;我们甚至都不需要去有意识地训练自己&#xff0c;就可以天赋一般地认识世界。对于机器而言&#xff0c;理解图片却…

MVC原理及案例分析

MVC原理及案例分析 关于MVC MVC全名是Model View Controller&#xff0c;是模型(model)&#xff0d;视图(view)&#xff0d;控制器(controller)的缩写&#xff0c;一种软件设计典范&#xff0c;用一种业务逻辑、数据、界面显示分离的方法组织代码&#xff0c;将业务逻辑聚集到…

人工智能的鱼与熊掌:精度与可解释性

来源&#xff1a;陈德旺科学网博客链接地址&#xff1a;http://blog.sciencenet.cn/blog-57940-1270913.html 人工智能自1956年诞生之日&#xff0c;就肩负用计算机程序模拟人类&#xff08;或生物体&#xff09;智能的初心与使命&#xff0c;从而理解智能的工作原理与运作机制…

MVC与三层架构的联系及三层架构实现学生注册功能

MVC与三层架构的联系及三层架构实现学生注册功能 三层架构的逻辑关系&#xff1a; MVC和三层架构的联系&#xff1a; 三层架构实现学生注册功能的逻辑&#xff1a; 学生注册页面&#xff1a; 输入学生信息&#xff1a; 完成学生注册: 代码实现&#xff1a; add.jsp <% …

MVC5+EF6 入门完整教程11--细说MVC中仓储模式的应用

MVC5EF6 入门完整教程11--细说MVC中仓储模式的应用 原文:MVC5EF6 入门完整教程11--细说MVC中仓储模式的应用摘要&#xff1a; 第一阶段1~10篇已经覆盖了MVC开发必要的基本知识。 第二阶段11&#xff5e;20篇将会侧重于专题的讲解&#xff0c;一篇文章解决一个实际问题。 根据…

Java Web实现信息管理

Java Web实现信息管理 前言&#xff1a; 大二上学期刚学完Oracle&#xff0c;老师就要求用Java语言操作Oracle&#xff0c;当时真的是懵了。回顾自己前两年的生活&#xff0c;大一上学期学习C语言&#xff0c;下学期学习Java&#xff0c;当时教课老师是学硬件的。课上讲一些理…

计算机科学界至今未解决的四大难题

作者&#xff1a;Shalitha Suranga译者&#xff1a;弯月 责编&#xff1a;张文出品&#xff1a;CSDN&#xff08;ID&#xff1a;CSDNnews&#xff09;在现实生活中&#xff0c;很多难题的解决方案都用到了计算机科学的基础理论。例如&#xff0c; Git 分布式版本控制系统建立…

按字编址与按字节编址

按字编址与按字节编址 要清楚按字编址和按字节编址的区别&#xff0c;先要知道 比特(bit)&#xff0c;字节(byte)&#xff0c;字(word) 之间的关系。 在计算机系统中&#xff0c;总线以固定大小的一块数据进行传输&#xff0c;这一块的数据也称为字(word)&#xff0c;如今的计…

2021年AI关键趋势,AI芯片初创公司可能发生并购

来源&#xff1a;雷锋网作者&#xff1a;包永刚编译&#xff1a;雷锋网人工智能&#xff08;AI&#xff09;和机器学习仍然是技术决策者、行业人士和投资者关注的重点。标普全球市场财智&#xff08;S&P Intelligence&#xff09;2020 7月发布的调查显示&#xff0c;有58%的…

CPU组成结构

CPU组成结构 CPU总体构图 CPU中央处理器&#xff08;Central Processing Unit&#xff09; CPU的结构框图&#xff1a;CPU内部由ALU&#xff08;算术逻辑单元&#xff09;、CU&#xff08;控制器&#xff09;、寄存器&#xff08;PC、IR、PSW、DR、通用寄存器等&#xff09;、…

每一个科学家的内心都住着一位哲学家(节选)

来源&#xff1a;腾讯大学&#xff08;ID: tencent_university)作者&#xff1a;张首晟&#xff08;斯坦福大学&#xff09;不少科学家的哲学造诣都很高。在哲学中&#xff0c;有着正负对立的世界观&#xff1a;有阴必有阳、有正必有负、有天使就会有魔鬼。这种哲学观念是如何在…

总结下载Spring Framework的jar包

总结下载Spring Framework的jar包 下载官网&#xff1a;Spring官网

ros2中gazebo安装的注意事项

Install From source&#xff08;推荐安装Fortress版本&#xff0c;好像很方便&#xff09; ROS Be sure youve installed ROS Humble (at least ROS-Base). More ROS dependencies will be installed below. Gazebo Install either Edifice, Fortress, or Garden.(没有har…

谷歌对2021年的六个预测:数据和云技术的革命即将到来

来源&#xff1a;AI前线作者&#xff1a;Debanjan Saha译者&#xff1a;平川策划&#xff1a;钰莹预测是充满挑战的&#xff0c;因为具体的预测取决于特定的时间框。但从云应用方面表现出的趋势来说&#xff0c;我们 2020 年看到的一些事情可能预示着 2021 年可能出现的变化。经…

Vue笔记:webpack项目vue启动流程

VUE启动流程 1. package.json 在执行npm run dev的时候&#xff0c;会在当前目录中寻找 package.json 文件, 有点类似 Maven 的 pom.xml 文件&#xff0c;包含项目的名称版本、项目依赖等相关信息。 { # 版本信息"name": "kitty-ui","version":…

哈工大等实现人工肌肉重大突破登上 Science!多国科学家联合实现全新驱动机理...

来源&#xff1a;雷锋网2021 年&#xff0c;机器人已经「成精」了&#xff0c;公然吵架、组团热舞再也不是人类专属。然鹅在很多人心里&#xff0c;机器人还是僵硬、机械甚至冰冷的。即便如此&#xff0c;技术日新月异&#xff0c;柔性机器人快速发展&#xff0c;我们对机器人的…

WOJ 18 动态无向图

一开始我是不会写的&#xff0c;后来点开了题解&#xff1a; 无话可说……那就写吧……然而第一发跑成暴力分&#xff0c;后来加了一个优化&#xff1a;就是在询问里面提到过的边都不用再加了。 然后……然后就过了呀…… 其实还有面向数据的编程的骚操作……既然卡过了那也没什…

AI如何帮助我们理解意识——麻省理工最新大脑研究

来源&#xff1a;ScienceAI编辑&#xff1a;文龙麻省理工学院和麻省总医院的一组研究人员最近发表了一项将社会意识与单个神经元活动联系起来的研究。据悉&#xff0c;这是首次在单神经元级别下找到「心智理论」的证据。测量大量的神经元是神经学的基础。即使是普通的核磁共振成…

计算机操作系统——处理机调度算法

计算机操作系统——处理机调度算法 一、处理机调度的层次和调度算法的目标 1.处理及调度的层次 高级调度&#xff1a;&#xff08;周期较长&#xff0c;大约几分钟一次&#xff09; 又称为长程调度或作业调度 调度对象&#xff1a;作业 功能&#xff1a;根据算法决定将外存中…

宇宙即计算~一种新科学:斯蒂芬·沃尔夫勒姆

编辑 &#xff1a;Gemini来源&#xff1a;人机与认知实验室斯蒂芬沃尔夫勒姆这个名字&#xff0c;在中文世界里可能远谈不上家喻户晓&#xff1b;但他的英文名Stephen Wolfram恐怕反而却要熟悉得多。他是Mathematica软件的发明者和首席设计师&#xff0c;被广泛地认为是当今科学…