QOJ.ac

QOJ

ID题目提交者结果用时内存语言文件大小提交时间测评时间
#564236#6419. Baby's First Suffix Array ProblemqwqUwU_TL 1ms4520kbC++143.0kb2024-09-14 21:24:102024-09-14 21:24:10

Judging History

你现在查看的是最新测评结果

  • [2024-09-14 21:24:10]
  • 评测
  • 测评结果:TL
  • 用时:1ms
  • 内存:4520kb
  • [2024-09-14 21:24:10]
  • 提交

answer

#include<bits/stdc++.h>
#define pb push_back
#define P make_pair
#define fi first
#define se second
#define bit(s,x) (((s)>>(x))&1)
#define pnp(s) __builtin_popcountll(s)
#define rep(i,a,b) for(int i=(a);i<=(b);++i)
#define per(i,a,b) for(int i=(a);i>=(b);--i)
using namespace std;
typedef long long ll; 
typedef unsigned long long ull;
typedef pair<int,int> pii;
inline ll read(){
	ll x=0,f=1,c=getchar();
	while(c<'0'||c>'9')f=(c=='-'?-1:1),c=getchar();
	while(c>='0'&&c<='9')x=(x<<1)+(x<<3)+(c^48),c=getchar();
	return x*f;
}
const int N=5e4+4;
int n,m,sa[N],rk[N],h[N];
char S[N];
inline void make(){
	static int old[N],cnt[N],id[N];
	int m=26;
	rep(i,1,n)++cnt[rk[i]=S[i]-'a'+1];
	rep(i,1,m)cnt[i]+=cnt[i-1];
	per(i,n,1)sa[cnt[rk[i]]--]=i;
	rep(i,1,m)cnt[i]=0;
	for(int w=1,p;;w<<=1,m=p){
		p=0;
		rep(i,n-w+1,n)id[++p]=i;
		rep(i,1,n)if(sa[i]>w)id[++p]=sa[i]-w;
		rep(i,1,n)++cnt[rk[i]];
		rep(i,1,m)cnt[i]+=cnt[i-1];
		per(i,n,1)sa[cnt[rk[id[i]]]--]=id[i],id[i]=0;
		rep(i,1,m)cnt[i]=0;
		swap(rk,old);p=0;
		rep(i,1,n)rk[sa[i]]=(old[sa[i]]==old[sa[i-1]]&&old[sa[i]+w]==old[sa[i-1]+w])?p:++p;
		if(p==n)break;
	}
	rep(i,2,n){
		int &k=h[rk[i]]=max(0,h[rk[i-1]]-1);
		while(S[i+k]==S[sa[rk[i]-1]+k])++k;
	}
}
struct Node{ int l,r,k,id;};
int ans[N];
#define lb(x) (x&-x)
int t[N];
inline void ad(int x,int k){for(;x<=n;x+=lb(x))t[x]+=k;}
inline int qr(int l,int r){
	if(l>r)return 0;
	int res=0; 
	for(;r>0;r-=lb(r))res+=t[r];
	for(--l;l>0;l-=lb(l))res-=t[l];
	return res;
}
int s[N];
inline void solve(int l,int r,vector<Node>&vec){
	if(l==r)return;
	vector<Node>v1,v2;int m=(l+r)>>1;
	for(auto tmp:vec){
		if(rk[tmp.k]<=m)v1.pb(tmp);
		else v2.pb(tmp);
	}
	solve(l,m,v1),solve(m+1,r,v2);
	s[m]=INT_MAX; per(i,m-1,l)s[i]=min(s[i+1],h[i+1]);
	s[m+1]=h[m+1];rep(i,m+2,r)s[i]=min(s[i-1],h[i]);
	static int id[N];rep(i,l,r)id[i]=i;
	sort(v1.begin(),v1.end(),[](Node A,Node B){return A.r>B.r;});
	sort(id+m+1,id+r+1,[&](int i,int j){return s[i]+sa[i]>s[j]+sa[j];});
	int j=m+1;
	for(auto tmp:v1){
		while(j<=r && s[id[j]]+sa[id[j]]>=tmp.r+1)ad(n-sa[id[j++]]+1,1);
		ans[tmp.id]+=qr(n-tmp.r+1,n-max(max(tmp.l,tmp.k),tmp.r-s[rk[tmp.k]]+1)+1);
	}
	rep(jj,m+1,j-1)ad(n-sa[id[jj]]+1,-1);
	sort(v2.begin(),v2.end(),[](Node A,Node B){return A.r-A.k<B.r-B.k;});
	sort(id+l,id+m+1,[&](int i,int j){return s[i]<s[j];});
	int i=l;
	for(auto tmp:v2)if(s[rk[tmp.k]]>=tmp.r-tmp.k+1){
		while(i<=m && s[id[i]]<tmp.r-tmp.k+1)ad(sa[id[i++]],1);
		ans[tmp.id]+=qr(tmp.l,tmp.k);
	}
	while(i<=m)ad(sa[id[i++]],1);
	for(auto tmp:v2){
		if(s[rk[tmp.k]]<tmp.r-tmp.k+1)ans[tmp.id]+=qr(tmp.l,tmp.r);
		else ans[tmp.id]+=qr(tmp.k,tmp.r);
	}
	rep(i,l,m)ad(sa[i],-1);
}
inline void solve(){
	n=read(),m=read(); scanf("%s",S+1); make();
	vector<Node>vec(m);
	rep(i,0,m-1)vec[i].l=read(),vec[i].r=read(),vec[i].k=read(),vec[i].id=i+1;
	solve(1,n,vec);
	rep(i,1,m)printf("%d\n",ans[i]+1),ans[i]=0;
}
int main() {
    //freopen("data.in", "r", stdin);
    //freopen("myans.out","w",stdout);
	int T=read();while(T--)solve();
    return 0;
}

详细

Test #1:

score: 100
Accepted
time: 1ms
memory: 4520kb

input:

2
10 4
baaabbabba
2 8 3
1 1 1
2 3 2
2 5 4
20 3
cccbccbadaacbbbcccab
14 17 16
3 20 17
17 20 18

output:

2
1
2
3
4
15
3

result:

ok 7 numbers

Test #2:

score: -100
Time Limit Exceeded

input:

8994
10 10
abaabbaabb
2 8 3
1 8 5
6 9 6
9 9 9
5 10 7
5 7 7
7 8 7
5 6 6
1 9 9
3 9 5
2 1
ab
1 2 1
8 6
bbabaabb
3 7 7
5 7 7
1 5 1
1 4 3
3 5 3
5 5 5
10 3
aababbaaab
3 4 4
6 9 8
4 6 6
7 3
babbaab
5 6 5
3 6 6
1 6 6
9 3
baaaabbba
2 5 2
8 9 8
1 4 4
9 2
babaababa
2 4 4
2 6 3
2 3
ba
1 2 2
1 2 1
2 2 2
10 2
aba...

output:


result: