Cod sursa(job #175396)

Utilizator sima_cotizoSima Cotizo sima_cotizo Data 9 aprilie 2008 21:39:41
Problema Substr Scor 100
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.46 kb
// 191.substr.cpp

#include <algorithm>
#include <fstream>
#include <iostream>
#include <iterator>
using namespace std;
#define MAX_S 16490
#define MAX_L 25
#define f first
#define s second

typedef pair<int,int> ii;
int n, k, lg, mx;
char S[MAX_S];
int P[MAX_L][MAX_S];
int O[MAX_S];
ii L[MAX_S];

struct comp {
	bool operator() (const int &a, const int &b) { return L[a] < L[b]; }
};
struct comp2 {
	bool operator()(const int &a, const int &b) { return P[lg][a] < P[lg][b]; }
};


void suffix_array() {
	int i, k, st, nr;
	for ( i=0; i<n; ++i ) 
		P[0][i] = S[i] - 'a';

	for ( k=1, st=1; st < n; ++k, st<<=1 ) {
		for ( i=0; i<n; ++i )
			L[i].f = P[k-1][i],
			L[i].s = i+st < n ? P[k-1][i+st] : -1,
			O[i] = i;
		sort(O, O+n, comp());
		
		P[k][ O[0] ] = nr=0;
		for ( i=1; i<n; ++i )
        	if ( L[O[i]] == L[O[i-1]] )
				P[k][ O[i] ] = nr;
            else
            	P[k][ O[i] ] = ++nr;
		
//		copy(P[k], P[k]+n, ostream_iterator<int>(cerr, " "));
//		cerr << "\n";
	}
	lg = k-1;
	for ( i=0; i<n; ++i ) O[i] = i;
	sort(O, O+n, comp2());
}

int LCP(int a, int b) {
	int tot = 0, k;
	if ( a==b ) return n-a;
	for ( k=lg; k+1; --k ) {
		if (P[k][a] == P[k][b]) 
			tot += 1<<k,
			a += 1<<k,
			b += 1<<k;
	}
	return tot;
}

int main() {
	freopen("substr.in", "r", stdin);
	freopen("substr.out", "w", stdout);
	
	scanf("%d %d\n", &n, &k);
	fgets(S, MAX_S, stdin);

	suffix_array();
	for ( int i=0; i<n-k; ++i )
		mx = max(mx, LCP(O[i], O[i+k-1]));

	printf("%d\n", mx);
	return 0;
}