Pagini recente » Cod sursa (job #2176192) | Cod sursa (job #488485) | Cod sursa (job #2739843) | Cod sursa (job #1808860) | Cod sursa (job #454883)
Cod sursa(job #454883)
#include <cstdlib>
#include <cstdio>
#include <algorithm>
#include <vector>
#include <cstring>
#define NMAX 17000
#define INF -1
typedef struct
{
int half1, half2, val;
}
SUF;
using namespace std;
int size, cnt, k, log;
char text[NMAX], word[100];
int order[2][NMAX], pos[NMAX], marked[NMAX];
int arr[16][NMAX], curr = 0;
int sufCmp(const SUF& lVal, const SUF& rVal)
{
return lVal.half1 != rVal.half1 ? lVal.half1 < rVal.half1 : lVal.half2 < rVal.half2;
}
void buildSuffixArray()
{
int lbl = 0, i, old, tmp;
memset(pos, 0, sizeof(pos));
for (i = 0; size - i; ++i) ++pos[text[i]];
for (i = 1; 200 - i; ++i) pos[i] += pos[i - 1];
for (i = size - 1; i + 1; --i) order[curr][--pos[text[i]]] = i;
arr[0][order[curr][0]] = 0;
for (i = 1; size - i; ++i) arr[0][order[curr][i]] = !(text[order[curr][i]] - text[order[curr][i - 1]]) ? arr[0][order[curr][i - 1]] : ++lbl;
for (int lg = 1, cnt = 1; log - lg + 1; ++lg, cnt <<= 1)
{
old = curr, tmp;
curr ^= 1;
memset(pos, 0, sizeof(pos));
memset(marked, 0, sizeof(marked));
for (i = 0; size - i; ++i) ++pos[arr[lg - 1][i]];
for (i = 1; lbl - i + 1; ++i) pos[i] += pos[i - 1];
for (i = size - 1; i >= 0; --i)
if ((tmp = order[old][i] - cnt) >= 0) order[curr][--pos[arr[lg - 1][tmp]]] = tmp, marked[tmp] = 1;
for (i = size - 1; i >= 0; --i)
if (!marked[i]) order[curr][--pos[arr[lg - 1][i]]] = i;
lbl = arr[lg][order[curr][0]] = 0;
for (i = 1; size - i; ++i)
arr[lg][order[curr][i]] = !(arr[lg - 1][order[curr][i]] - arr[lg - 1][order[curr][i - 1]]) &&
!(arr[lg - 1][order[curr][i] + cnt] - arr[lg - 1][order[curr][i - 1] + cnt]) ? arr[lg][order[curr][i - 1]] : ++lbl;
}
}
int lcp(int i1, int i2)
{
if (i1 == i2) return size - i1 + 1;
int len = 0;
for (cnt = log; (i1 + (1 << cnt) >= size) && (i2 + (1 << cnt) >= size); --cnt);
for (int ceva = 1 << cnt; cnt >= 0 && i1 < size && i2 < size; --cnt, ceva >>= 1)
if (!(arr[cnt][i1] - arr[cnt][i2]))
len += ceva, i1 += ceva, i2 += ceva;
return len;
}
int main()
{
FILE *fin = fopen("substr.in", "r"), *fout = freopen("substr.out", "w", stdout);
fscanf(fin, "%d %d\n", &size, &k);
if (k == 1)
{
printf("%d\n", size);
return 0;
}
while (1 << (log + 1) < size) ++log;
fread(text, 1, size, fin);
buildSuffixArray();
int best = 0;
for (int i = 0; i < size - k; ++i)
best = max(best, lcp(order[curr][i], order[curr][i + k - 1]));
printf("%d\n", best);
return 0;
}