Bzoj 4556: [Tjoi2016&Heoi2016]字符串
4556: [Tjoi2016&Heoi2016]字符串
Time Limit: 20 Sec Memory Limit: 128 MB
Submit: 177 Solved: 92
[Submit][Status][Discuss]
Description
Input
Output
对于每一次询问,输出答案。
Sample Input
aaaaa
1 1 1 5
1 5 1 1
2 3 2 3
2 4 2 3
2 3 2 4
Sample Output
1
2
2
2
HINT
Source
#include<bits/stdc++.h>
using namespace std;
#define MAXN 100010
int root[MAXN],Ws[MAXN],wa[MAXN],wb[MAXN],sa[MAXN],wv[MAXN],Rank[MAXN],height[MAXN],MN[MAXN][17],sum[MAXN*18],ls[MAXN*18],rs[MAXN*18],SIZE;
char str[MAXN];
int read()
{
int s=0,fh=1;char ch=getchar();
while(ch<'0'||ch>'9'){if(ch=='-')fh=-1;ch=getchar();}
while(ch>='0'&&ch<='9'){s=s*10+(ch-'0');ch=getchar();}
return s*fh;
}
int cmp(int *r,int a,int b,int l){return (r[a]==r[b])&&(r[a+l]==r[b+l]);}
void DA(char *r,int *sa,int n,int m)
{
int i,j,p,*x=wa,*y=wb,*t;
for(i=0;i<m;i++)Ws[i]=0;
for(i=0;i<n;i++)Ws[x[i]=r[i]]++;
for(i=0;i<m;i++)Ws[i]+=Ws[i-1];
for(i=n-1;i>=0;i--)sa[--Ws[x[i]]]=i;
for(j=1,p=1;p<n;j*=2,m=p)
{
for(p=0,i=n-j;i<n;i++)y[p++]=i;
for(i=0;i<n;i++)if(sa[i]>=j)y[p++]=sa[i]-j;
for(i=0;i<n;i++)wv[i]=x[y[i]];
for(i=0;i<m;i++)Ws[i]=0;
for(i=0;i<n;i++)Ws[wv[i]]++;
for(i=0;i<m;i++)Ws[i]+=Ws[i-1];
for(i=n-1;i>=0;i--)sa[--Ws[wv[i]]]=y[i];
for(t=x,x=y,y=t,p=1,x[sa[0]]=0,i=1;i<n;i++)
x[sa[i]]=cmp(y,sa[i-1],sa[i],j)?p-1:p++;
}
}
void calheight(int n)
{
int i,j,k=0;
for(i=1;i<=n;i++)Rank[sa[i]]=i;
for(i=0;i<n;height[Rank[i++]]=k)
for(k?k--:0,j=sa[Rank[i]-1];str[i+k]==str[j+k];k++);
}
void ST(int n)
{
int i,j;
for(i=1;i<=n;i++)MN[i][0]=height[i];
for(j=1;(1<<j)<=n;j++)
{
for(i=1;i+(1<<j)-1<=n;i++)
{
MN[i][j]=min(MN[i][j-1],MN[i+(1<<(j-1))][j-1]);
}
}
}
void Insert(int x,int &y,int l,int r,int I)
{
y=++SIZE;
sum[y]=sum[x]+1;
if(l==r)return;
int mid=(l+r)/2;
ls[y]=ls[x];rs[y]=rs[x];
if(I<=mid)Insert(ls[x],ls[y],l,mid,I);
else Insert(rs[x],rs[y],mid+1,r,I);
}
int Query(int x,int y,int l,int r,int ql,int qr)
{
if(ql<=l&&r<=qr)return sum[y]-sum[x];
int mid=(l+r)/2;
if(qr<=mid)return Query(ls[x],ls[y],l,mid,ql,qr);
else if(ql>mid)return Query(rs[x],rs[y],mid+1,r,ql,qr);
else return Query(ls[x],ls[y],l,mid,ql,mid)+Query(rs[x],rs[y],mid+1,r,mid+1,qr);
}
int main()
{
freopen("heoi2016_str.in","r",stdin);
freopen("heoi2016_str.out","w",stdout);
int n,m,lstr,i,s1,s2,s3,s4,wz,l,r,ans,j,mid,last,next,MID,wz1,wz2;
n=read();m=read();
scanf("\n%s",str);
lstr=strlen(str);
str[lstr+1]=0;
DA(str,sa,lstr+1,256);
calheight(lstr);
ST(lstr);
SIZE=0;
for(i=lstr;i>=1;i--)Rank[i]=Rank[i-1];
for(i=1;i<=n;i++)Insert(root[i-1],root[i],1,n,Rank[i]);
for(i=1;i<=m;i++)
{
s1=read();s2=read();s3=read();s4=read();
wz=Rank[s3];
l=1;r=min(s2-s1+1,s4-s3+1);ans=0;
while(l<=r)
{
mid=(l+r)/2;
wz1=wz2=wz;MID=mid;
for(j=16;j>=0;j--)if(wz1>=(1<<j)&&MN[wz1-(1<<j)+1][j]>=MID)wz1-=(1<<j);
for(j=16;j>=0;j--)if(wz2+(1<<j)<=n&&MN[wz2+1][j]>=MID)wz2+=(1<<j);
if(Query(root[s1-1],root[s2-mid+1],1,n,wz1,wz2)>0){ans=mid;l=mid+1;}
else r=mid-1;
}
printf("%d\n",ans);
}
fclose(stdin);
fclose(stdout);
return 0;
}
Bzoj 4556: [Tjoi2016&Heoi2016]字符串的更多相关文章
- ●BZOJ 4556 [Tjoi2016&Heoi2016]字符串
题链: http://www.lydsy.com/JudgeOnline/problem.php?id=4556 题解: 巨恶心...但是题很好呀,可以练习好几个比较麻烦的算法~ 1).预处理 首先用 ...
- BZOJ 4556: [Tjoi2016&Heoi2016]字符串(后缀数组 + 二分答案 + 主席树 + ST表 or 后缀数组 + 暴力)
题意 一个长为 \(n\) 的字符串 \(s\),和 \(m\) 个询问.每次询问有 \(4\) 个参数分别为 \(a,b,c,d\). 要你告诉它 \(s[a...b]\) 中的所有子串 和 \(s ...
- bzoj 4556 [Tjoi2016&Heoi2016]字符串——后缀数组+主席树
题目:https://www.lydsy.com/JudgeOnline/problem.php?id=4556 本来只要查 ht[ ] 数组上的前驱和后继就行,但有长度的限制.可以二分答案解决!然后 ...
- BZOJ 4556 [Tjoi2016&Heoi2016]字符串 ——后缀数组 ST表 主席树 二分答案
Solution 1: 后缀数组暴力大法好 #include <map> #include <cmath> #include <queue> #include &l ...
- 4556: [Tjoi2016&Heoi2016]字符串
4556: [Tjoi2016&Heoi2016]字符串 链接 分析: 首先可以二分这个长度.此时需要判断是否存在一个以b结尾的前缀,满足与[c,d]的lcp大于等于mid. 如果我们把串翻转 ...
- Bzoj4556: [Tjoi2016&Heoi2016]字符串 后缀数组
4556: [Tjoi2016&Heoi2016]字符串 Time Limit: 20 Sec Memory Limit: 128 MBSubmit: 169 Solved: 87[Sub ...
- [BZOJ4556][Tjoi2016&Heoi2016]字符串 后缀数组+主席树
4556: [Tjoi2016&Heoi2016]字符串 Time Limit: 20 Sec Memory Limit: 128 MB Description 佳媛姐姐过生日的时候,她的小 ...
- [BZOJ4556][TJOI2016&&HEOI2016]字符串(二分答案+后缀数组+RMQ+主席树)
4556: [Tjoi2016&Heoi2016]字符串 Time Limit: 20 Sec Memory Limit: 128 MBSubmit: 1360 Solved: 545[S ...
- [BZOJ4556][Tjoi2016&Heoi2016]字符串 主席树+二分+倍增+后缀自动机
4556: [Tjoi2016&Heoi2016]字符串 Time Limit: 20 Sec Memory Limit: 128 MBSubmit: 1215 Solved: 484[S ...
随机推荐
- Spring MVC控制层的返回类型--String类型与Bean类型
SpringMVC控制层的返回类型形式多样,现拿其中的两种--String类型与Bean类型作以说明. 一.测试项目的结构 说明:(jsp的名字没起好) 控制层:UserController.java ...
- Searching in a rotated and sorted array
Given a sorted array that has been rotated serveral times. Write code to find an element in this arr ...
- c#带参数和返回值的函数 开启线程调用的方法
public delegate string DgTest(); private void btn_District_Click(object sender, EventArgs e) { //实例化 ...
- 团体程序设计天梯赛-练习集L1-002. 打印沙漏
L1-002. 打印沙漏 时间限制 400 ms 内存限制 65536 kB 代码长度限制 8000 B 判题程序 Standard 作者 陈越 本题要求你写个程序把给定的符号打印成沙漏的形状.例如给 ...
- uva 701
参考了一下http://hi.baidu.com/renxl51/item/e80b688f9f54aadd5e0ec1de 给一个数字x,求最小的正整数e,使得pow(2,e) == x*pow(1 ...
- Eclipse 插件开发 —— 深入理解查找(Search)功能及其扩展点
引言 查找功能是计算机语言开发环境 / 平台的一个非常重要的特性.Eclipse 也不例外,它提供了丰富的查找功能(用户可以输入正则表达式或任意字符串,指定查找范围和匹配选项等等),并且提供了简单易用 ...
- CodeForce 339:A+B+C
A题:水题.. #include<stdio.h> #include<string.h> ; char s[ maxn ]; int main(){ //freopen(&qu ...
- SaaS系列介绍之二: SaaS介绍
1 引言 横看成岭侧成峰,远近高低各不同. 不识庐山真面目, 只缘身在此山中. ________苏轼, ...
- vim查找/替换字符串 及一些高级用法
例: 32 ./run 0_39.pkt 0_39.jpg 33 ./run 0_3.pkt 0_3.jpg 34 ./run 0_40.pkt 0_40.jpg 35 ./run 0_41.pkt ...
- *J2EE中乱码处理
发生中文乱码有三种情况 表单form (1)post 首先确定浏览器的编码方式,比如说utf-8,请求发给web服务器,web服务器以编码方式iso-9959-1来接收数据(服务器是外国人编写的),服 ...