Cod sursa(job #2386032)

Utilizator Vlad_lsc2008Lungu Vlad Vlad_lsc2008 Data 22 martie 2019 02:14:51
Problema Substr Scor 70
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 2.77 kb
#include <iostream>
#include <fstream>
#include <algorithm>
#include <vector>
#define DIM 16390
using namespace std;

int n,k;

struct sufix
{
    int ms,md;
    int poz;

    bool operator < (const sufix s) const
    {
        if(ms==s.ms)
            return md<s.md;
        return ms< s.ms;
    }
};

char txt[DIM];
sufix mat[20][DIM];
int position[20][DIM];
int poz[DIM];

int cif[2][30];

int lcp(int p1,int p2,int num)
{
   // cout<<p1<<' '<<p2<<' '<<num<<'\n';
    int i,rez;
    rez=0;
    if(p1==p2) return n;
    for(i=num;i>=0;i--)
    {
     //   cout<<i<<' '<<p1<<' '<<p2<<' '<<position[i][p1]<<' '<<position[i][p2]<<'\n';
        if(position[i][p1]==position[i][p2])
        {
            rez+=(1<<i);
            p1+=(1<<i);
            p2+=(1<<i);
            if(p1>=n || p2>=n) break;
        }
    }
    return rez;
}

int main()
{
    ios_base::sync_with_stdio(false);
    ifstream t1("substr.in");
    ofstream t2("substr.out");
    t1>>n>>k; t1.get();
    t1.get(txt,16390);


    int i,j;

    for(i=0;i<n;i++)
        cif[0][ txt[i]-'a']++;

    int crt=0;
    for(i='a';i<='z';i++)
        if(cif[0][i-'a'] && !cif[1][i-'a'])
            cif[1][i-'a']=crt++;

    for(i=0;i<n;i++)
    {
        mat[0][i].ms=cif[1][ txt[i]-'a'];
        mat[0][i].md=0;
        mat[0][i].poz=i;
        position[0][i]=cif[1][txt[i]-'a'];
    }

    int num=0;

    for(int p=1;p<=2*n;p*=2,num++)
    {

        sort(mat[num],mat[num]+n);

        poz[0]=0;
        for(i=1;i<n;i++)
            if( mat[num][i].ms==mat[num][i-1].ms && mat[num][i].md==mat[num][i-1].md && mat[num][i].md!=-1)
                poz[i]=poz[i-1];
            else
                poz[i]=poz[i-1]+1;

        if(p!=1)
        for(i=0;i<n;i++)
            position[num][ mat[num][i].poz ] = poz[i] ;


        for(i=0;i<n;i++)
        {

            mat[num+1][ mat[num][i].poz ].ms=poz[i];

            if( mat[num][i].poz-p >=0 )
                mat[num+1][ mat[num][i].poz-p ].md=poz[i];

            mat[num+1][ mat[num][i].poz].poz= mat[num][i].poz;
        }

        for(i=n-1; i>n-2*p; i--)
            mat[num+1][i].md=-1;

    }

    for(i=0;i<n;i++) poz[ position[num-1][i] ] = i ;

    /*cout<<'\n';

    for(i=0;i<num;i++)
    {
        for(j=0;j<n;j++) cout<<mat[i][j].ms<<' '<<mat[i][j].md<<' '<<mat[i][j].poz<<"    "; cout<<'\n';
    } cout<<'\n';

    for(i=0;i<num;i++)
    {
        for(j=0;j<n;j++) cout<<position[i][j]+1<<' '; cout<<'\n';
    }

    cout<<'\n'/
    for(i=0;i<n;i++) cout<<poz[i]+1<<' '; cout<<'\n'; cout<<'\n';*/

    num--;
    int sol=0;
    for(i=0;i<=n-k;i++)
        sol=max(sol, lcp( poz[i], poz[i+k-1],num) );
    t2<<sol<<'\n';
    t1.close();
    t2.close();
    return 0;
}