您的位置:首页 > 其它

poj 1743

2015-03-17 19:34 113 查看
题意:给出一个串,求两个不相交的长度相等的子串,使得对应位置的差相等。

题解:首先,假设串是a[0],a[1],...a
,先作差,即a[1]=a[1]-a[0],a[2]=a[2]-a[1],a[i]=a[i]-a[i-1],然后我们求a[1],a[2],a[3],...a
的两个不相交的公共子串。

先将h数组求出来,然后二分子串长度,。。。。

#include <cstdio>
#include <cstring>
#include <iostream>
#define maxn 20010
using namespace std;

int n;
int aa[maxn], sa[maxn], rk[maxn], ht[maxn], vv[maxn];

void expand( int k, int sa[maxn], int rk[maxn], int tsa[maxn], int trk[maxn] ) {
for( int i=1; i<=n; i++ ) vv[rk[sa[i]]]=i;
for( int i=n; i>=1; i-- ) if( sa[i]>k ) tsa[vv[rk[sa[i]-k]]--]=sa[i]-k;
for( int i=n-k+1; i<=n; i++ ) tsa[vv[rk[i]]--]=i;
for( int i=1; i<=n; i++ ) trk[tsa[i]]=trk[tsa[i-1]]+(rk[tsa[i]]!=rk[tsa[i-1]]||rk[tsa[i]+k]!=rk[tsa[i-1]+k]);
}
void calcht() {
int k=0;
ht[sa[1]]=0;
for( int i=1; i<=n; i++ ) {
if( rk[i]==1 ) continue;
int j=sa[rk[i]-1];
while( aa[i+k]==aa[j+k] ) k++;
ht[i] = k;
if( k>0 ) k--;
}
}
void suffix() {
static int tsa[maxn], trk[maxn];
for( int i=1; i<=180; i++ ) vv[i]=0;
for( int i=1; i<=n; i++ ) vv[aa[i]]++;
for( int i=1; i<=180; i++ ) vv[i]+=vv[i-1];
for( int i=1; i<=n; i++ ) sa[vv[aa[i]]--]=i;
for( int i=1; i<=n; i++ ) rk[sa[i]]=rk[sa[i-1]]+(aa[sa[i]]!=aa[sa[i-1]]);
int *pa=sa, *pb=rk, *pc=tsa, *pd=trk;
for( int k=1; k<n; k<<=1,swap(pa,pc),swap(pb,pd) )
expand(k,pa,pb,pc,pd);
if( pa!=sa ) memcpy( sa, tsa, sizeof(sa) ), memcpy( rk, trk, sizeof(rk) );
calcht();
}
bool ok( int len ) {    //    len>=1
int top, minp, maxp;
top = minp = maxp = sa[1];
for( int i=2; i<=n; i++ ) {
if( ht[sa[i]]<len ) {
if( maxp-minp>=len ) return true;
top = minp = maxp = sa[i];
} else {
if( minp>sa[i] ) minp=sa[i];
if( maxp<sa[i] ) maxp=sa[i];
}
}
if( maxp-minp>=len ) return true;
return false;
}
int main() {
while( scanf("%d",&n)==1 ) {
if( n==0 ) break;
n--;
for( int i=0; i<=n; i++ )
scanf( "%d", aa+i );
for( int i=n; i>=1; i-- )
aa[i]=aa[i]-aa[i-1]+88;
suffix();
int lf=0, rg=n/2;
while( lf<rg ) {
int mid=(lf+rg+1)>>1;
if( ok(mid) ) lf=mid;
else rg=mid-1;
}
lf++;
printf( "%d\n", lf<5 ? 0 : lf  );
}
}


View Code
内容来自用户分享和网络整理,不保证内容的准确性,如有侵权内容,可联系管理员处理 点击这里给我发消息
标签: