Cod sursa(job #1123346)

Utilizator cosmyoPaunel Cosmin cosmyo Data 26 februarie 2014 00:47:50
Problema Substr Scor 100
Compilator cpp Status done
Runda Teme Pregatire ACM Unibuc 2013 Marime 2.22 kb
#include <string>
#include <algorithm>
#include <fstream>
#include <vector>
#include <cstdio>
using namespace std;
const int N = 1 << 18;
const int M = 19;

struct entry {
  pair<int, int> nr;
  int index;
} ;
string s;
bool cmp(const entry &a, const entry &b) {
  return a.nr < b.nr;
}

class SuffixArray {
  private:
    int n;
    int m;
    string s;
    vector<int> array[M];
    vector<entry> l;
  public:
    SuffixArray(string given) : s(given) {
      n = s.size();
      m = 1;
      array[0] = vector<int>(n);
      for(int i = 1; i <= n; i<<=1, ++m) {
        array[m] = vector<int>(n);
      }
      array[m] = vector<int>(n);
      for(int i = 0; i < n; ++i) {
        array[0][i] = s[i];
      }
      l.resize(n);
    }
    void build() {
      for(int stp = 1, cnt = 1; stp <= m; ++stp, cnt <<= 1) {
        for(int i = 0; i < n; ++i) {
          l[i].nr.first = array[stp - 1][i];
          l[i].nr.second = (i + cnt < n) ? array[stp - 1][i + cnt] : - 1;
          l[i].index = i;
        }
        sort(l.begin(), l.end(), cmp);
        for(int i = 0; i < n; ++i)
        {
          if(i > 0 && l[i].nr.first == l[i - 1].nr.first && 
                      l[i].nr.second == l[i - 1].nr.second) {
            array[stp][l[i].index] = array[stp][l[i - 1].index];
          } else {
            array[stp][l[i].index] = i;
          }
        }
       
      }
/*
      for(int i = 0; i <= m; ++i)
      {
        for(int j = 0; j < n; ++j)
        {
          printf("%d ", array[i][j]);
        }
        printf("\n");
      }
  */  }
    vector<int>& getArray() {
      return array[m];
    }

};

int main() {
  ifstream cin("substr.in");
  ofstream cout("substr.out");
  int n, k;
  cin >> n >> k;
  cin >> s;
  SuffixArray sa(s);
  sa.build();
  vector<int> &l = sa.getArray();
  vector<int> p(l.size());
  vector<int> o(l.size());
  int mx = 0;
  for(int i = 0; i < n; ++i)
  {
    p[l[i] + o[l[i]]++] = i;
  }
  for(int i = 0; i <= n - k; ++i) 
  {
    int length = 0;
    for(int j = p[i], r = p[i + k - 1]; s[j] == s[r] && j < s.size() && 
        r < s.size(); ++j, ++r, ++length) ;
//    cout << p[i] << " " << p[i + k - 1] << " " << length << '\n';
    if(length > mx)
    {
      mx = length;
    }
  }

  cout << mx << '\n';
  return 0;
}