Cod sursa(job #1764921)

Utilizator nnnmmmcioltan alex nnnmmm Data 26 septembrie 2016 09:04:09
Problema Substr Scor 100
Compilator cpp Status done
Runda cerculdeinfo-lectia1-hashuri.rabinkarp Marime 1.91 kb
#include<cstdio>
#include<cctype>
#include<cstring>
#include<vector>
const int MOD1=12731,MOD2=11563,NMAX=16385;
char s[NMAX];
std::vector<std::pair<int,int> > hashul[MOD1];
std::pair<int,int> put[NMAX];

int Calc_Put(int n)
{
 put[0]=std::make_pair(1,1);
 for(int i=1;i<=n;i++)
     {
      put[i].first=(put[i-1].first*63)%MOD1;
      put[i].second=(put[i-1].second*63)%MOD2;
     }
}

int Transforma(char x)
{
 if(isalpha(x))
    {
     if(x>'Z')
        return x-'a'+11;
     else
        return x-'A'+37;
    }
 else
    return x-'0'+1;
}

void Clear()
{
 memset(hashul,0,sizeof hashul);
}

void Add(int r1,int r2,int &max)
{
 for(int i=0;i<hashul[r1].size();i++)
     if(hashul[r1][i].first==r2)
        {
         max=std::max(max,++hashul[r1][i].second);
         return;
        }
 hashul[r1].push_back(std::make_pair(r2,1));
 max=std::max(max,1);
}

int Rabin_Karp(int l)
{
 int n=strlen(s),pos=0,val1=0,val2=0;
 int max=-1;
 for(int i=0;i<n;i++)
     {
      val1=(val1*63+Transforma(s[i]))%MOD1;
      val2=(val2*63+Transforma(s[i]))%MOD2;
      pos++;
      if(pos>l)
         {
          pos--;
          val1=(100*MOD1+val1-Transforma(s[i-l])*put[l].first)%MOD1;
          val2=(100*MOD2+val2-Transforma(s[i-l])*put[l].second)%MOD2;
         }
      if(pos==l)
         Add(val1,val2,max);
     }
 return max;
}

int Cautare_Binara(int n,int k)
{
 int st=1,dr=n,rasp;
 while(st<=dr)
       {
        int mij=(st+dr)/2;
        if(Rabin_Karp(mij)<k)
           {
            dr=mij-1;
           }
        else
           {
            st=mij+1;
            rasp=mij;
           }
       }
 return rasp;
}

int main()
{
 FILE *file=fopen("substr.in","r");
 int n,k;
 fscanf(file,"%d %d ",&n,&k);
 fscanf(file,"%s ",&s);
 fclose(file);
 file=fopen("substr.out","w");
 Calc_Put(n);
 fprintf(file,"%d\n",Cautare_Binara(n,k));
 fclose(file);
}