字符串
文章平均质量分 56
bubbleoooooo
这个作者很懒,什么都没留下…
展开
-
poj 3461 Oulipo (KMP 模板题)
直接套模板=w= #include #include char s[10010]; char t[1000100]; int nex[10010]; void getnext(char *s) { memset(nex,0,sizeof(nex)); int j=0,k=1; int len=strlen(s+1); nex[1]=0; while(k<=len){ if(原创 2015-03-19 14:22:54 · 368 阅读 · 0 评论 -
poj1226 Substrings (多串最长公共子串+正反)
字符串大暴力。 选出最短的串,暴力枚举每一个子串,正反两个,逐个匹配。 #include #include char dic[105][105]; char key[105]; char z[105],rev[105]; int ans; int main() { int t; scanf("%d",&t); while(t--){ int n; memset(k原创 2015-03-18 09:46:36 · 690 阅读 · 0 评论 -
poj 3167 Cow Patterns (kmp + 线段树/树状数组)
这道题确实让我更加深入的了解了kmp。。。。 以前的匹配只要字符或者是数值一样就可以,这道题是区间名次一样进行匹配的。 一个数在区间中的名次可以转化为,它前面比他小的数的个数,和他相等的个数,和比他大的个数。 一个数显然不行,但是如果一个区间内所有数的这三个值都对应相等,那么这两个区间就是等价的。 可以用线段树来维护区间。 #include #include #include #incl原创 2015-03-12 22:18:35 · 625 阅读 · 0 评论 -
HDU 4436 str2int 后缀数组(前缀和预处理)
题意: 给定n个包含(‘0’~‘9’)的字符串,求字符串不同子串的和。 首先对于n个字符串,我们通常是要用其他字符将其连成一个字符串的,这样便于用后缀数组进行处理。 其次,求不同子串,数量是n-sa[i]+1-height[i]. 新子串自然就从sa[i]~sa[i]+height[i]开始到,sa[i]~当前字符串结束为止(其他字符之前)为止,因为下一个就会包含两个字符串。 对于原创 2015-03-10 17:49:05 · 561 阅读 · 0 评论 -
poj 1200 Crazy Search(字符串hash)
这道题主要的理解在于输入的最后一句话 意思是nc^n 酱紫,就可以用n位nc进制来做了。。 附上代码喵: #include #include const int maxn=1010000; #define MIN(a,b) a<b?a:b typedef long long ll; char s[maxn]; int vis[300]; bool hash[16000005]; i原创 2015-03-21 22:27:08 · 466 阅读 · 0 评论 -
后缀数组总结
附模板(后缀数组) void build_sa(int m,int n){ int *x=wa,*y=wb,*t; for(int i=0;i<m;i++)c[i]=0; for(int i=0;i<n;i++)c[x[i]=id(s[i])]++; for(int i=1;i<m;i++)c[i]+=c[i-1]; for(int i=n-1;i>=0;i--)sa[--c[x[i]原创 2015-03-10 20:32:28 · 386 阅读 · 0 评论 -
hdu 3746 Cyclic Nacklace (kmp 最小重复子串补齐)
求出最小覆盖子串,取模补齐。 #include #include const int maxn=101000; #define MIN(a,b) a<b?a:b typedef long long ll; char s[maxn]; int next[maxn]; void getnext() { memset(next,0,sizeof(next)); int j=-1,k=0;原创 2015-03-21 21:43:33 · 372 阅读 · 0 评论 -
hdu 2594 Simpsons’ Hidden Talents(kmp模板)
直接把两个串连起来=_= 忘了考虑第二个串比第一个串短了=_= 附上代码喵: #include #include const int maxn=101000; #define MIN(a,b) a<b?a:b typedef long long ll; char s[maxn],p[maxn]; int next[maxn]; void getnext(int l) { m原创 2015-03-21 21:27:07 · 351 阅读 · 0 评论 -
hdu 3336 Count the string(KMP+dp)
利用next数组的性质。 next[i]表示1~i-1的后缀与1~next[i]-1前缀匹配。此前缀为可以匹配的最长前缀。 dp[i]表示以i结尾的不同前缀的数量。 转移方程就为dp[i]=dp[next[i]]+1;(加了0~si这个新前缀) 由于next的性质,包含的以 i 结尾的不同前缀的数量除了s0~si其他全在s0~snext[i]中出现过。 因为这是最长的匹配,原创 2015-03-21 20:59:09 · 329 阅读 · 0 评论 -
hdu 4622 Reincarnation(后缀数组)
求一个字串的不同字串有多少个。问不同的字串有多少个,即问对于每一个后缀,它的所有前缀中,与其他后缀的前缀不同的有几个。解法是按rank将后缀一个个加进来,那么每加进一个后缀,将会增加n-sa[i]+1个前缀,但这些前缀中,有一些是之前出现过的,之前出现过的个数就是i与之前加进来的所有后缀的最长公共前缀的长度,很显然,就是height[i]。那么每次能获得的不同的字串的个数就是n-sa[i]+1-h原创 2015-03-09 22:58:12 · 615 阅读 · 0 评论 -
poj 2752 Seek the Name, Seek the Fame(找出所有前缀等于后缀的位置)
直接用next数组往前找。 #include #include #include using namespace std; char name[400010]; int nex[400010]; void getnext() { memset(nex,0,sizeof(nex)); nex[0]=-1; int j=-1,k=0; int len=strlen(name); while原创 2015-03-20 17:17:08 · 446 阅读 · 0 评论 -
poj 1961 Period (最小重复子串 kmp)
最小覆盖子串长度为n-next[n] ,n为字符串长度。如果恰好覆盖就为n/(n-next[n]),否则为1. 所有前缀的最小重复子串,加一个循环即可。 附上代码喵: #include #include #include using namespace std; char name[1000010]; int nex[1000010]; void getnext() { memse原创 2015-03-20 21:23:03 · 548 阅读 · 0 评论 -
poj 2406 Power Strings (最小重复子串出现次数 kmp)
最小覆盖子串长度为n-next[n] ,n为字符串长度。如果恰好覆盖就为n-next[n],否则为1. #include #include #include using namespace std; char name[1000010]; int nex[1000010]; void getnext() { memset(nex,0,sizeof(nex)); nex[0]=-1;原创 2015-03-20 17:36:51 · 412 阅读 · 0 评论 -
poj 2185 Milking Grid (最小覆盖矩阵)
给一个字符矩阵,求最小覆盖矩阵的面积。 有一个结论:最小覆盖子串(串尾多一小段时,用前缀覆盖)长度为n-next[n](n-pre[n]),n为串长。 #include #include char dic[10010][101]; char temp[105]; int suc[105]; int nex[10010]; int main() { int r,c; while(sc原创 2015-03-20 16:41:51 · 566 阅读 · 0 评论 -
hdu 2087 剪花布条(不重叠匹配 kmp)
模式串的不重叠匹配,每次匹配完后模式串指针指向0即可。 附上代码喵: #include #include #include using namespace std; char s[1010],t[1010]; int nex[1010]; void getnext() { memset(nex,0,sizeof(nex)); nex[0]=-1; int j=-1,k=0;原创 2015-03-20 21:38:54 · 723 阅读 · 0 评论 -
kmp模板
void getnext() { memset(nex,0,sizeof(nex)); nex[0]=-1; int j=-1,k=0; int len=strlen(t); while(k<len) { if(j==-1||s[j]==s[k]) { j++;k++; nex[k]=j; } else j=nex[j]; } } void kmp(原创 2015-03-20 21:41:19 · 310 阅读 · 0 评论 -
poj 3080 Blue Jeans (多串最长公共子串 暴力)
#include #include char str[20][101]; char key[160]; char miao[106]; int main() { int t; scanf("%d",&t); while(t--){ int n; scanf("%d",&n); memset(miao,0,sizeof(miao)); for(int i=0;i<n;i++)原创 2015-03-20 15:53:53 · 497 阅读 · 0 评论 -
poj 3450 Corporate Identity(后缀数组+二分)
求多串最长公共子串,直接用后缀数组解即可。 虽然要求输出字典序,但是因为check的时候是从字典序小的开始,满足条件直接返回的第一个即为字典序最小。 附代码喵: #include #include const int maxn=810010; char key[400]; int s[maxn];//int 开成char re到死=_= int pos[maxn]; int原创 2015-03-18 19:49:08 · 562 阅读 · 1 评论