Cod sursa(job #181529)

Utilizator vlad_popaVlad Popa vlad_popa Data 18 aprilie 2008 14:52:38
Problema Substr Scor 90
Compilator cpp Status done
Runda Arhiva de probleme Marime 1.59 kb
#include <cstdio>
#include <cstring>
#include <algorithm>

using namespace std;

#define MAXN 1<<15
#define f first
#define s second
#define mp make_pair
#define ppi pair < pair <int, int>, int >

char sir[MAXN];
int N, K;
int step;
int P[20][MAXN];
ppi L[MAXN];

void Suff_Array ()
{
    int i, log;
    for (i = 0, N = strlen(sir); i < N; ++ i)
        P[0][i] = sir[i] - 'a';

    for (step = log = 1; log <= N; log <<= 1, ++ step)
    {
        for (i = 0; i < N; ++ i)
        {
            L[i].f.f = P[step-1][i];
            L[i].f.s = (i + log < N) ? P[step-1][i + log] : (-1);
            L[i].s = i;
        }
        sort (L, L + N);
        
        for (i = 0; i < N; ++ i)
            if (i > 0 && L[i-1].f.f == L[i].f.f && L[i-1].f.s == L[i].f.s)
                P[step][L[i].s] = P[step][L[i-1].s];
            else P[step][L[i].s] = i;
    }        
}

int LCP (int x, int y)
{
    if (x == y) return N - x;
    
    int match = 0, stp = step;
    for (; stp >= 0 && x < N && y < N; -- stp)
        if (P[stp][x] == P[stp][y]) 
            x += (1<<stp), y += (1<<stp), match += (1<<stp);
    
    return match;
}

void solve ()
{
    Suff_Array ();
    -- step;
    
    int i, sol = 0;
    for (i = 0; i <= N - K; ++ i)
        sol = max (sol, LCP(L[i].s, L[i + K - 1].s));
        
    printf ("%d\n", sol);
}

int
 main ()
{
    freopen ("substr.in", "rt", stdin);
    freopen ("substr.out", "wt", stdout);
    
    scanf ("%d %d\n", &N, &K);
    --N;
    fgets (sir, MAXN, stdin);
    
    solve ();
    
    return 0;
}