[BZOJ3230] Similar string suffix array +rmq

Source: Internet
Author: User

3230: Similar substring

Time limit:20 Sec Memory limit:128 MB

Description

Input

Enter line 1th, which contains 3 integer n,q. Q represents the number of inquiry groups.
Line 2nd is the string s.
Next Q line, two integers i and j per line. (1≤I≤J).

Output

Output a total of Q lines, a number per line represents the answer for each group of queries. If there is no string I or J substring, then output-1.

Sample Input

5 3
Ababa
3 5
5 9
8 10

Sample Output

18
16
-1

HINT

Sample explanation

The 1th group asks: Two substrings are "ABA", "Ababa". F = 32 + 32 = 18.

The 2nd group asks: Two substrings are "Ababa", "Baba". f = 02 + 42 = 16.

Group 3rd asks: there is no 10th substring. Output-1. Data range

n≤100000,q≤100000, the string consists of a lowercase letter ' a ' ~ ' Z '

Solution: The first thing we want to solve is the essentially different substring count problem:

Given that the substring must be prefixed with a suffix, we add each suffix in rank order,

Then each new suffix will produce a new prefix (substring) n-sa+1

But because of the existence of LCP, these substrings and the previous string of repetition of some

so the final formula is σn-sa+1-height, and of course specific details, such as ±1 will be slightly different with the style of the code and the way of calculation, The reader can modify it by itself

And then we thought, the point is, let's just ask for the longest common prefix and the longest public suffix of some two substrings.

So we can run an SA and then reverse the string, we get a suffix array and a weird "prefix array".

Then we find the sub-string corresponding to the endpoint and suffix, and then use RMQ to calculate the LCP interval minimum value can be.

Code implementation (at that time I was transferred to the confusion and then encapsulated 233):

1#include <cstdio>2#include <cstring>3#include <algorithm>4 using namespacestd;5typedefLong LongLL;6 Const intn=100010;7 intn,xx[n],yy[n],cnt[n],bin[ at];8 LL Num[n];9 structFleetTen { One     intsa[n],height[n],rank[n],f[n][ -]; A     CharS[n]; -     inti,j,k,p,m; -InlinevoidGet_sa () the     { -         int*x=xx,*y=yy;m= the; -          for(i=0; i<m;++i) cnt[i]=0; -          for(i=0; i<n;++i) ++cnt[x[i]=S[i]]; +          for(i=1; i<m;++i) cnt[i]+=cnt[i-1]; -          for(i=n-1; ~i;--i) sa[--cnt[x[i]]]=i; +          for(k=1, p=0;p <n&&k<=n;k<<=1, m=p) A         { at              for(p=0, I=n-k;i<n;++i) y[p++]=i; -              for(i=0; i<n;++i)if(sa[i]>=k) y[p++]=sa[i]-K; -              for(i=0; i<m;++i) cnt[i]=0; -              for(i=0; i<n;++i) + +Cnt[x[y[i]]; -              for(i=1; i<m;++i) cnt[i]+=cnt[i-1]; -              for(i=n-1; ~i;--i) sa[--cnt[x[y[i]]]]=Y[i]; in              for(Swap (x, y), p=1, x[sa[0]]=0, i=1; i<n;++i) -X[sa[i]]= (y[sa[i]]==y[sa[i-1]]&&y[sa[i]+k]==y[sa[i-1]+k])? p1:p + +; to         } +     } -InlinevoidGet_rank () the     { *          for(i=0; i<n;++i) rank[sa[i]]=i; $          for(k=i=0; i<n;height[rank[i++]]=k)Panax Notoginseng              for(k=k?k-1: k,j=sa[rank[i]-1];s[i+k]==s[j+k];++k); -     } theInlinevoidST () +     { A          for(i=0; i<n;++i) f[i][0]=Height[i]; the          for(i=1; bin[i]<=n;++i) +              for(j=0; j+bin[i]-1<n;++j) -F[j][i]=min (f[j][i-1],f[j+bin[i-1]][i-1]); $     } $Inline LL Query (intLintR) -     { -         intlen=r-l+1, k=0; the          while(bin[k+1]<=len) + +K; -         returnMin (f[l][k],f[r-bin[k]+1][k]);Wuyi     } theInlinevoidGet_kth (int&st,int&ed,ll RK) -     { Wu         intAns=lower_bound (NUM,NUM+N,RK)-num; -st=sa[ans],ed=st+height[ans]-1+rk-num[ans-1]; About     } $Inlinevoidintn () - {Get_sa (), Get_rank (), ST ();} -InlinevoidCalc () -{ for(i=0; i<n;++i) num[i]=num[i-1]+ll (n-sa[i]-height[i]-1);} A }sfx,pre; + Inline ll get_length (ll Id1,ll id2) the { -Registerinti,j,k,st[2],ed[2]; $Sfx.get_kth (st[0],ed[0],id1); theSfx.get_kth (st[1],ed[1],id2); theLL Val=min (ed[0]+1ll-st[0],ed[1]+1ll-st[1]), tmp=Val; the     if(st[0]!=st[1]) the         if(sfx.rank[st[0]]<sfx.rank[st[1]]) -Tmp=min (Tmp,sfx.query (sfx.rank[st[0]]+1, sfx.rank[st[1]])); in         Else theTmp=min (Tmp,sfx.query (sfx.rank[st[1]]+1, sfx.rank[st[0]])); theed[0]=n-2-ed[0],ed[1]=n-2-ed[1]; About     if(ed[0]!=ed[1]) the         if(pre.rank[ed[0]]<pre.rank[ed[1]]) theVal=min (Val,pre.query (pre.rank[ed[0]]+1, pre.rank[ed[1]])); the         Else +Val=min (Val,pre.query (pre.rank[ed[1]]+1, pre.rank[ed[0]])); -     returntmp*tmp+val*Val; the }Bayi intMain () the { theRegisterinti,j,m,a,b,q; LL u,v; -scanf"%d%d%s",&n,&m,sfx.s); -      for(bin[0]=i=1; i<= -; ++i) bin[i]=bin[i-1]<<1; the      for(i=1; i<=n;++i) pre.s[i-1]=sfx.s[n-i]; thesfx.s[n]=pre.s[n]=1, n++; the Sfx.intn (); PRE.INTN (); Sfx.calc (); the      while(m--) -     { thescanf"%lld%lld",&u,&v); the         if(u>num[n-1]|| v>num[n-1]) printf ("-1\n"); the         Elseprintf"%lld\n", Get_length (u,v));94     } the}

[BZOJ3230] Similar string suffix array +rmq

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.