码迷,mamicode.com
首页 > 编程语言 > 详细

BZOJ3172 后缀数组

时间:2014-11-05 21:09:31      阅读:320      评论:0      收藏:0      [点我收藏+]

标签:style   blog   http   io   color   ar   os   for   sp   

题意:求出一篇文章中每个单词的出现次数

 

表示样例没看懂= =,为什么aaa的次数是1但aa的次数是3啊......

 

标准解法好像是AC自动机or后缀自动机,还有人用KMP暴力过的= =

用后缀数组做的。原来没刷过这种类型,顺便复习一下~

Reference:http://blog.sina.com.cn/s/blog_6e63f59e0101bpw5.html

 

以样例为例:

bubuko.com,布布扣

对于每个单词第一个字母对应的height,向上、向下数出height值大于等于单词长度的height的个数。

注意细节的处理= =

 

 1 //在BT5下attack的时候把数值调大点(超过2000)就行了,具体可以参见网上破解无线网密码的文章,就是抓包之后的那步,注入数据包的命令
 2 #include "iostream"
 3 #include "cstring"
 4 using namespace std;
 5 #define maxn 1010000
 6 
 7 int wa[maxn],wb[maxn],wv[maxn],wws[maxn];
 8 int rank[maxn],height[maxn];
 9 int r[maxn],sa[maxn],ans[maxn],st[maxn],ln[maxn];
10 int n,len,tl;
11 char ts[maxn];
12 
13 int cmp(int *r,int a,int b,int l)
14 {
15     return r[a]==r[b]&&r[a+l]==r[b+l];
16 }
17 
18 void da(int *r,int *sa,int n,int m)
19 {
20     int i,j,p,*x=wa,*y=wb,*t;
21     for(i=0; i<m; i++) wws[i]=0;
22     for(i=0; i<n; i++) wws[x[i]=r[i]]++;
23     for(i=1; i<m; i++) wws[i]+=wws[i-1];
24     for(i=n-1; i>=0; i--) sa[--wws[x[i]]]=i;
25     for(j=1,p=1; p<n; j*=2,m=p)
26     {
27 
28         for(p=0,i=n-j; i<n; i++) y[p++]=i;
29         for(i=0; i<n; i++) if(sa[i]>=j) y[p++]=sa[i]-j;
30         for(i=0; i<n; i++) wv[i]=x[y[i]];
31         for(i=0; i<m; i++) wws[i]=0;
32         for(i=0; i<n; i++) wws[wv[i]]++;
33         for(i=1; i<m; i++) wws[i]+=wws[i-1];
34         for(i=n-1; i>=0; i--) sa[--wws[wv[i]]]=y[i];
35         for(t=x,x=y,y=t,p=1,x[sa[0]]=0,i=1; i<n; i++)
36             x[sa[i]]=cmp(y,sa[i-1],sa[i],j)?p-1:p++;
37     }
38     return;
39 }
40 
41 void calheight(int *r,int *sa,int n)
42 {
43     int i,j,k=0;
44     for(i=1; i<=n; i++) rank[sa[i]]=i;
45     for(i=0; i<n; height[rank[i++]]=k)
46         for(k?k--:0,j=sa[rank[i]-1]; r[i+k]==r[j+k]; k++);
47     return;
48 }
49 
50 int main()
51 {
52     ios::sync_with_stdio(false);
53     cin>>n;
54     len=0;
55     for (int i=1;i<=n;i++)
56     {
57         st[i]=len;
58         cin>>ts;
59         tl=strlen(ts);
60         ln[i]=tl;
61         for (int j=len;j<len+tl;j++)
62         {
63             char ch=ts[j-len];
64             int tn=ch;
65             r[j]=tn;
66         }
67         len+=tl;
68         r[len]=1;
69         len++;
70     }
71     r[len]=0;
72 
73     da(r,sa,len+1,200);
74     calheight(r,sa,len);
75 
76     //for (int i=0;i<=len+1;i++)
77     //    cout<<height[i]<<" ";
78     //cout<<endl;
79     for (int i=1;i<=n;i++)
80     {
81         int tmp=rank[st[i]];
82         int tl=tmp,tr=tmp+1,tlen=ln[i];
83         while ((height[tl]>=tlen)&&(tl>=0))      tl--;
84         while ((height[tr]>=tlen)&&(tr<=len))   tr++;
85         cout<<tr-tl<<endl;
86     }
87 
88     return 0;
89 }

 

BZOJ3172 后缀数组

标签:style   blog   http   io   color   ar   os   for   sp   

原文地址:http://www.cnblogs.com/pdev/p/4077122.html

(0)
(0)
   
举报
评论 一句话评论(0
登录后才能评论!
© 2014 mamicode.com 版权所有  联系我们:gaon5@hotmail.com
迷上了代码!