Cod sursa(job #788683)

Utilizator SchumiDumitru Andrei Georgian Schumi Data 15 septembrie 2012 16:24:30
Problema PScPld Scor 60
Compilator cpp Status done
Runda Arhiva de probleme Marime 0.99 kb
#include <cassert>
#include <cstdio>

#include <algorithm>
using namespace std;

const int N = 1000005;

int n;
int d[N * 2];
char c;
char text[N * 2];
long long sol;

int extinde(int x, int y) {
	int len = y - x + 1;
	int i = x - (y - x) - 1;
	int j = y + 1;
	while (i > 0 && j <= n && text[i] == text[j]) {
		--i;
		++j;
		++len;
	}
	
	return len;
}

int main() {
	assert(freopen("pscpld.in", "r", stdin) != NULL);
	assert(freopen("pscpld.out", "w", stdout) != NULL);
	
	text[++n] = '#';	
	while (scanf(" %c ", &c) == 1) {
		text[++n] = c;
		text[++n] = '#';
	}
	
	int j = 1;
	d[1] = 1;
	for (int i = 2; i <= n; ++i) {
		int iPrim = j - (i - j);
		
		if ((iPrim - d[iPrim] + 1 <= j - d[j]+ 1) || (d[j] + j - 1 <= i)) {
			d[i] = extinde(i, max(i, j + d[j] - 1));
			j = i;
		} else
			d[i] = d[iPrim];
	}
	
	for (int i = 1; i <= n; ++i)
		if (d[i] % 2 == 0)
			sol += d[i] / 2;
		else
			sol += (d[i] - 1) / 2;
	
	printf("%lld\n", sol);
	
	return 0;
}