Problem p03364 (C++)

Buggy submission (status: Time Limit Exceeded):
#include <iostream>
#include <vector>
using namespace std;

struct RollingHash {
  int n;
  vector<long long> base, mod;
  vector<vector<long long>> hash, power;
  RollingHash(string s) {
    base = {1009, 9973};
    mod = {1000000007, 1000000009};
    n = s.size();
    hash = vector<vector<long long>>(n + 1, vector<long long>(2));
    power = vector<vector<long long>>(n + 1, vector<long long>(2, 1));
    for (int i = 0; i < n; ++i) {
      for (int j = 0; j < 2; ++j) {
        hash[i + 1][j] = (hash[i][j] + s[i]) * base[j] % mod[j];
        power[i + 1][j] = power[i][j] * base[j] % mod[j];
      }
    }
  }
  vector<long long> get(int l, int r) { //[l,r)
    vector<long long> ret(2);
    for (int i = 0; i < 2; ++i)
      ret[i] = ((hash[r][i] - hash[l][i] * power[r - l][i]) % mod[i] + mod[i]) %
               mod[i];
    return ret;
  }
};

struct RollingHash_64 {
  int n;
  unsigned long long base;
  vector<long long> hash, power;
  RollingHash_64(string s) {
    base = 1e9 + 7;
    n = s.size();
    hash = vector<long long>(n + 1);
    power = vector<long long>(n + 1, 1);
    for (int i = 0; i < n; ++i) {
      hash[i + 1] = (hash[i] + s[i]) * base;
      power[i + 1] = power[i] * base;
    }
  }
  unsigned long long get(int l, int r) { //[l,r)
    return hash[r] - hash[l] * power[r - l];
  }
};

int main() {
  int N;
  cin >> N;
  vector<string> S(2 * N);
  for (int i = 0; i < N; ++i) {
    cin >> S[i];
    S[i] += S[i];
    S[i + N] = S[i];
  }
  vector<RollingHash> H, V;
  int N_ = 2 * N;
  for (int i = 0; i < N_; ++i)
    V.emplace_back(S[i]);
  for (int j = 0; j < N_; ++j) {
    string s;
    for (int i = 0; i < N_; ++i) {
      s += S[i][j];
    }
    H.emplace_back(s);
  }
  int ans = 0;
  for (int i = 0; i < N; ++i) {
    for (int j = 0; j < N; ++j) {
      bool f = true;
      for (int k = 0; k < N; ++k) {
        auto v = V[i + k].get(j, j + N), h = H[j + k].get(i, i + N);
        if (v != h) {
          f = false;
          break;
        }
      }
      if (f)
        ++ans;
    }
  }
  cout << ans << endl;
  return 0;
}


Fixed submission:
#include <iostream>
#include <vector>
using namespace std;

struct RollingHash {
  int n;
  vector<long long> base, mod;
  vector<vector<long long>> hash, power;
  RollingHash(string s) {
    base = {1009, 9973};
    mod = {1000000007, 1000000009};
    n = s.size();
    hash = vector<vector<long long>>(n + 1, vector<long long>(2));
    power = vector<vector<long long>>(n + 1, vector<long long>(2, 1));
    for (int i = 0; i < n; ++i) {
      for (int j = 0; j < 2; ++j) {
        hash[i + 1][j] = (hash[i][j] + s[i]) * base[j] % mod[j];
        power[i + 1][j] = power[i][j] * base[j] % mod[j];
      }
    }
  }
  vector<long long> get(int l, int r) { //[l,r)
    vector<long long> ret(2);
    for (int i = 0; i < 2; ++i)
      ret[i] = ((hash[r][i] - hash[l][i] * power[r - l][i]) % mod[i] + mod[i]) %
               mod[i];
    return ret;
  }
};

struct RollingHash_64 {
  int n;
  unsigned long long base;
  vector<long long> hash, power;
  RollingHash_64(string s) {
    base = 1e9 + 7;
    n = s.size();
    hash = vector<long long>(n + 1);
    power = vector<long long>(n + 1, 1);
    for (int i = 0; i < n; ++i) {
      hash[i + 1] = (hash[i] + s[i]) * base;
      power[i + 1] = power[i] * base;
    }
  }
  unsigned long long get(int l, int r) { //[l,r)
    return hash[r] - hash[l] * power[r - l];
  }
};

int main() {
  int N;
  cin >> N;
  vector<string> S(2 * N);
  for (int i = 0; i < N; ++i) {
    cin >> S[i];
    S[i] += S[i];
    S[i + N] = S[i];
  }
  vector<RollingHash_64> H, V;
  int N_ = 2 * N;
  for (int i = 0; i < N_; ++i)
    V.emplace_back(S[i]);
  for (int j = 0; j < N_; ++j) {
    string s;
    for (int i = 0; i < N_; ++i) {
      s += S[i][j];
    }
    H.emplace_back(s);
  }
  int ans = 0;
  for (int i = 0; i < N; ++i) {
    for (int j = 0; j < N; ++j) {
      bool f = true;
      for (int k = 0; k < N; ++k) {
        auto v = V[i + k].get(j, j + N), h = H[j + k].get(i, i + N);
        if (v != h) {
          f = false;
          break;
        }
      }
      if (f)
        ++ans;
    }
  }
  cout << ans << endl;
  return 0;
}