Cod sursa(job #2494137)

Utilizator MiricaMateiMirica Matei MiricaMatei Data 17 noiembrie 2019 13:25:04
Problema PScPld Scor 40
Compilator cpp-64 Status done
Runda Arhiva de probleme Marime 1.76 kb
#include <bits/stdc++.h>

using namespace std;

const int MAXN = 1000000;
const int SIGMA = 26;

struct PalTree {
  int length;
  int dp;
  PalTree* failLink;
  PalTree* children[SIGMA];

  PalTree() {
    length = 0;
    dp = 0;
    failLink = NULL;
    for (int i = 0; i < SIGMA; ++i)
      children[i] = NULL;
  }
};

char s[MAXN + 5];
int n;
long long ans;

void citire() {
  scanf("%s", s + 1);
  n = strlen(s + 1);
}

void buildPalTree() {
  PalTree* rootEven = new PalTree();
  PalTree* rootOdd = new PalTree();
  rootEven->length = 0;
  rootEven->dp = 0;
  rootEven->failLink = rootOdd;
  rootOdd->length = -1;
  rootOdd->dp = 0;
  rootOdd->failLink = rootOdd;

  PalTree* curPal = rootOdd;
  int last = 0;
  for (int i = 1; i <= n; ++i) {
    while (s[i] != s[i - curPal->length - 1])
      curPal = curPal->failLink;
    PalTree* tmp;
    if (curPal->children[s[i] - 'a'] == NULL) {
      tmp = curPal->failLink;
      while (tmp != rootOdd && (tmp->children[s[i] - 'a'] == NULL || s[i] != s[i - tmp->length - 1]))
        tmp = tmp->failLink;
      int dp = 0;
      if (tmp->children[s[i] - 'a'] == NULL) {
        tmp = rootEven;
      } else {
        tmp = tmp->children[s[i] - 'a'];
        dp = tmp->dp;
      }
      curPal->children[s[i] - 'a'] = new PalTree();
      curPal->children[s[i] - 'a']->length = 2 + curPal->length;
      curPal->children[s[i] - 'a']->dp = 1 + dp;
      curPal->children[s[i] - 'a']->failLink = tmp;
    }
    curPal = curPal->children[s[i] - 'a'];
    ans += curPal->dp;
  }
}

void afisare() {
  printf("%lld\n", ans);
}

int main() {
  freopen("pscpld.in", "r", stdin);
  freopen("pscpld.out", "w", stdout);

  citire();
  buildPalTree();
  afisare();

  return 0;
}