Cod sursa(job #425561)

Utilizator ssergiussSergiu-Ioan Ungur ssergiuss Data 25 martie 2010 21:09:07
Problema Substr Scor 90
Compilator cpp Status done
Runda Arhiva de probleme Marime 2.7 kb
#include <algorithm>
#include <cassert>
#include <fstream>

using namespace std;

#define Input "substr.in"
#define Output "substr.out"

#define Dim 16384 + 5
#define Log 14 + 5

struct suffix {

    int f, s, p;
};

char A[Dim];
int N, K, Sol, P[Log][Dim];
int cnt, ord[Dim];
suffix L[Dim];

struct cmp {

    bool operator()( const suffix &a, const suffix &b ) {

        return (a.f < b.f) || (a.f == b.f && a.s < b.s);
    }
};

struct cmp_2 {

    bool operator()( const int &x, const int &y ) {

        return P[cnt][x] < P[cnt][y];
    }
};

int lcp( int x, int y ) {

    int i, sol;

    if( x == y )
        return N - x;

    sol = 0;
    for( i = cnt; i >= 0 && x < N && y < N; --i )
        if( P[i][x] == P[i][y] ) {

            x += (1 << i);
            y += (1 << i);
            sol += (1 << i);
        }

    return sol;
}

int main() {

    ifstream fin( Input );
    ofstream fout( Output );

    int i, j;

    fin >> N >> K;
    fin.ignore( 1, '\n' );
    fin.getline( A, Dim );

    assert( strlen( A ) );

//    for( i = 0; i < N; ++i ) {
//
//        L[i].f = A[i];
//        L[i].s = -1;
//        L[i].p = i;
//    }

//    sort( L, L + N, cmp() );

//    for( i = 0; i < N; ++i )
//        if( i > 0 && L[i].f == L[i - 1].f && L[i].s == L[i - 1].s )
//            P[0][L[i].p] = P[0][L[i - 1].p];
//        else
//            P[0][L[i].p] = i;

    for( i = 0; i < N; ++i )
        P[0][i] = A[i];

    for( i = 1; (1 << i) <= N; ++i ) {

        for( j = 0; j < N; ++j ) {

            L[j].f = P[i - 1][j];
            if( j + (1 << (i - 1)) < N )
                L[j].s = P[i - 1][j + (1 << (i - 1))];
            else
                L[j].s = -1;
            L[j].p = j;
        }

        sort( L, L + N, cmp() );

        for( j = 0; j < N; ++j )
            if( j > 0 && L[j].f == L[j - 1].f && L[j].s == L[j - 1].s )
                P[i][L[j].p] = P[i][L[j - 1].p];
            else
                P[i][L[j].p] = j;
    }

    cnt = i - 1;

//    for( int i = 0; i < N; ++i )
//        fout << L[i].p << "\n";

//    fout << cnt;

    for( i = 0; i < N; ++i )
        ord[i] = i;
    sort( ord, ord + N, cmp_2() );

//    for( int i = 0; i < N; ++i )
//        fout << ord[i] << "\n";

//    for( int i = 0; i < N; ++i ) {
//
//        for( int j = ord[i]; j < N; ++j )
//            fout << A[j];
//        fout << "\n";
//    }

//    for( int i = 0; i < N - K; ++i )
//        aux = lcp( ord[i], ord[i + K - 1] );

    for( i = 0; i < N - K; ++i )
        Sol = max( Sol, lcp( ord[i], ord[i + K - 1] ) );

    fout << Sol;

    fin.close();
    fout.close();

    return 0;
}