LA 3942 Remember the Word(字典树/树上dp)
来源:互联网 发布:主播直播软件 编辑:程序博客网 时间:2024/05/23 19:11
题目,给出3w长度的字符串,一部字典 4000个长度不超过100的单词
把该字符串可以分解成x个字典的单词为一种合法方案
求出该该字符串的所有分解方案数,对20071027取模
思路:dp[i]表示 从第i个字符开始到结尾的一个子串
dp递推;dp[i]=sum(dp[ i+len(x) ]) x为 子串S【i,结尾】的前缀
显然把单词做成字典树,每次对查询前缀x,看x在树种能遇到几个单词结束标记,由于单词长度最大100,所以查询最大复杂度o(100)
对于长度为n的字符串,要查询n次前缀,每次o(100),总复杂度 n*o(100)
也就是o(10^7)。。。数据比较弱。。所以69ms就过了
这次了解到一个就是 query函数 的 X的len由于是递减的,,所以只要在外面传进去就好。。。而之前手残地写了n=strlen(s)。。导致最后时间跑了2秒多。。。去掉后就是69ms了
#include <cstdio>#include <cmath>#include <cstring>#include <string>#include <algorithm>#include <iostream>#include <queue>#include <map> #include <vector>using namespace std;#define inf 2147483647const int N = 300010; const int mod=20071027;const int maxnode = 400110; int dp[N]; char tm[N];//inline int idx(char c) {return c-'a';} int len; struct trie{int ch[maxnode][26];int val[maxnode];int sz;void init(){sz=1;val[0]=0;//可不需要memset(ch[0],0,sizeof(ch[0]));}int idx(char c) {return c-'a';}void insert(char *s ){int u=0,n=strlen(s),i;for (i=0;i<n;i++){int c=idx(s[i]);if (!ch[u][c]){memset(ch[sz],0,sizeof(ch[sz]));val[sz]=0;ch[u][c]=sz++;}u=ch[u][c];}val[u]=n;//标记当前单词权值(暂且当作字符串结尾标记)}/*int query_if(char *s)//查找当前单词是否存在,本题用不上{int u=0,n=strlen(s),i;for (i=0;i<n;i++){int c=idx(s[i]);if (!ch[u][c])return 0;else{u=ch[u][c];} }return val[u]; }*/int query(char *s,int p,int n)//查找该字符串的前缀能匹配上多少个单词{int u=0,i; //n=strlen(s);之前没把n传进来,而是脑残写下了这句,导致耗时2S+,去掉了69msfor (i=0;i<n;i++){int c=idx(s[i]);if (!ch[u][c])return 0; if (val[ch[u][c]]){if (p+i==len-1)dp[p]+=1;elsedp[p]=(dp[p]+dp[p+i+1])%mod; }u=ch[u][c]; }return 0;}};trie tp;int main(){char tmp[105];int cnt=1;while( scanf("%s", &tm)!=EOF){tp.init(); int n,i,j;scanf("%d",&n);len=strlen(tm);for (i=1;i<=n;i++){scanf("%s",&tmp);tp.insert(tmp);}for (i=len-1;i>=0;i--){ dp[i]=0;tp.query(tm+i,i,len-i); }printf("Case %d: %d\n",cnt++,dp[0]%mod);//输出结果忘记取模wa几次}return 0;}
0 0
- LA 3942 Remember the Word(字典树/树上dp)
- LA 3942 Remember the Word(前缀树&树上DP)
- LA 3942 - Remember the Word 字典树 dp
- LA 3942 - Remember the Word 字典树+DP
- UVA 1401 & LA 3942 Remember the Word 字典树+DP
- LA 3942 Remember the Word——DP + 字典树
- 单词拆解&前缀树&树上DP LA 3942 Remember the Word
- LA 3942 Remember the word(字典树加DP)wa到吐血。。
- LA 3942 Remember the Word(Trie+DP)
- LA 3942 Remember the Word / 前缀树 + DP
- (LA 3942)Remember the Word --DP+Trie树
- LA 3942 Remember the Word Trie树 DP
- UVALive 3942 Remember the Word 字典树DP&&前缀树
- uvalive 3942 Remember the Word 字典树+dp
- UVALive - 3942 Remember the Word(字典树+dp)
- UVALive 3942 Remember the Word(字典树+dp)
- UVALive 3942Remember the Word(字典树 + 简单dp)
- uvalive 3942 Remember the Word (字典树+DP)
- XML工具代码:SAX从String字符串XML内获取指定节点或属性的值
- 《老情书.张嘉佳》读后感
- 1、8天学通MongoDB
- Shell脚本中变量$
- while中尽量不使用Continue,不论什么编程语言
- LA 3942 Remember the Word(字典树/树上dp)
- 计蒜客 第2题:整除问题
- Android SQLite 显式事务控制优化插入数据
- RTP/RTCP协议介绍
- TYVJ 2218 最大矩阵
- 《要么读书,要么旅行,身体和灵魂总有一个在路上》读后感
- 特别注意:Delphi数组的赋值,SetLength没有作用
- 2、Mongodb快速入门之使用Java操作Mongodb
- 面试题 22