Problem p03678 (C++)

Buggy submission (status: Runtime Error):
#include <bits/stdc++.h>
#define XX first
#define YY second
#define pb emplace_back
#define FOR(i, a, b) for (int(i) = (a); i < (b); ++(i))
#define EFOR(i, a, b) for (int(i) = (a); i <= (b); ++(i))
#define rep(X, Y) for (int(X) = 0; (X) < (Y); ++(X))
#define REP rep
#define rrep(X, Y) for (int(X) = (Y)-1; (X) >= 0; --(X))
#define all(X) (X).begin(), (X).end()
#define eb emplace_back

using namespace std;
typedef long long ll;
typedef pair<int, int> pii;
typedef pair<ll, ll> pll;
typedef ll LL;
typedef pii PII;
typedef pll PLL;
const ll MOD = 1e9 + 7;

#define rall(X) (X).rbegin(), (X).rend()
#define UNIQUE(X) (X).erase(unique(all(X)), (X).end())
#define reps(X, S, Y) for (int(X) = S; (X) < (Y); ++(X))
#define rreps(X, S, Y) for (int(X) = (Y)-1; (X) >= (S); --(X))
template <class T> inline bool MX(T &l, const T &r) {
  return l < r ? l = r, 1 : 0;
}
template <class T> inline bool MN(T &l, const T &r) {
  return l > r ? l = r, 1 : 0;
}

string S;
LL L, R;
using V = array<LL, 26>;

// re[i] := S[0..i-1]の接頭辞・接尾辞が最大何文字一致しているか
void mp(const string &S, vector<int> &re) {
  re.resize(S.size() + 1);
  re[0] = -1;
  int j = -1;
  rep(i, S.size()) {
    while (j >= 0 && S[i] != S[j])
      j = re[j];
    re[i + 1] = ++j;
  }
}

V Count(string &s) {
  V ret = {};
  for (char c : s) {
    ret[c - 'a']++;
  }
  return ret;
}

LL Sum(V &a) {
  LL ret = 0;
  rep(i, 26) { ret += a[i]; }
  return ret;
}

V Solve(LL r) {
  V ret = {};
  if (!r)
    return ret;

  if (S.size() * 2 >= r) {
    string SS = S + S;
    rep(i, r) { ret[SS[i] - 'a']++; }
    return ret;
  }

  vector<int> re;
  mp(S, re);
  int n = S.size();
  int w = n - re[n];
  string P = S.substr(0, w);
  auto a = Count(P);
  if (n % w == 0) {
    rep(i, 26) { ret[i] += a[i] * (r / w); }
    rep(i, r % w) { ret[P[i] - 'a']++; }
    return ret;
  }

  vector<V> series;
  series.eb(a);
  series.eb(Count(S));
  int idx = 1;
  while (1) {
    if (Sum(series[idx]) * 2 >= r) {
      assert(Sum(series[idx]) < r);
      {
        ret = series[idx];
        r -= Sum(series[idx]);
      }
      break;
    }

    series.eb();
    rep(i, 26) { series.back()[i] = series[idx - 1][i] + series[idx][i]; }
    ++idx;
  }

  while (idx > 1) {
    // cout << "r: " << r << endl;
    // cout << idx << ": ";
    // rep(i, 26) {
    //   if (i) cout << " ";
    //   cout << ret[i];
    // }cout << endl;
    assert(Sum(series[idx]) >= r);
    --idx;
    if (Sum(series[idx]) <= r) {
      rep(i, 26) ret[i] += series[idx][i];
      r -= Sum(series[idx]);
      --idx;
    }
  }
  if (idx == 1) {
    assert(r <= S.size());
    rep(i, r) { ret[P[i] - 'a']++; }
  } else {
    assert(idx == 0 && Sum(series[idx]) >= r);
    assert(r <= w);
    rep(i, r) { ret[P[i] - 'a']++; }
  }
  return ret;
}

signed main() {
  ios_base::sync_with_stdio(false);
  cout << fixed << setprecision(0);

  cin >> S;
  assert(S.size() % 2 == 0);
  S = S.substr(S.size() / 2);
  cin >> L >> R;
  auto ans = Solve(R);
  auto sub = Solve(L - 1);
  rep(i, 26) {
    if (i)
      cout << " ";
    assert(ans[i] >= sub[i]);
    cout << ans[i] - sub[i];
  }
  cout << endl;
}


Fixed submission:
#include <bits/stdc++.h>
#define XX first
#define YY second
#define pb emplace_back
#define FOR(i, a, b) for (int(i) = (a); i < (b); ++(i))
#define EFOR(i, a, b) for (int(i) = (a); i <= (b); ++(i))
#define rep(X, Y) for (int(X) = 0; (X) < (Y); ++(X))
#define REP rep
#define rrep(X, Y) for (int(X) = (Y)-1; (X) >= 0; --(X))
#define all(X) (X).begin(), (X).end()
#define eb emplace_back

using namespace std;
typedef long long ll;
typedef pair<int, int> pii;
typedef pair<ll, ll> pll;
typedef ll LL;
typedef pii PII;
typedef pll PLL;
const ll MOD = 1e9 + 7;

#define rall(X) (X).rbegin(), (X).rend()
#define UNIQUE(X) (X).erase(unique(all(X)), (X).end())
#define reps(X, S, Y) for (int(X) = S; (X) < (Y); ++(X))
#define rreps(X, S, Y) for (int(X) = (Y)-1; (X) >= (S); --(X))
template <class T> inline bool MX(T &l, const T &r) {
  return l < r ? l = r, 1 : 0;
}
template <class T> inline bool MN(T &l, const T &r) {
  return l > r ? l = r, 1 : 0;
}

string S;
LL L, R;
using V = array<LL, 26>;

// re[i] := S[0..i-1]の接頭辞・接尾辞が最大何文字一致しているか
void mp(const string &S, vector<int> &re) {
  re.resize(S.size() + 1);
  re[0] = -1;
  int j = -1;
  rep(i, S.size()) {
    while (j >= 0 && S[i] != S[j])
      j = re[j];
    re[i + 1] = ++j;
  }
}

V Count(string &s) {
  V ret = {};
  for (char c : s) {
    ret[c - 'a']++;
  }
  return ret;
}

LL Sum(V &a) {
  LL ret = 0;
  rep(i, 26) { ret += a[i]; }
  return ret;
}

V Solve(LL r) {
  V ret = {};
  if (!r)
    return ret;

  if (S.size() * 2 >= r) {
    string SS = S + S;
    rep(i, r) { ret[SS[i] - 'a']++; }
    return ret;
  }

  vector<int> re;
  mp(S, re);
  int n = S.size();
  int w = n - re[n];
  string P = S.substr(0, w);
  auto a = Count(P);
  if (n % w == 0) {
    rep(i, 26) { ret[i] += a[i] * (r / w); }
    rep(i, r % w) { ret[P[i] - 'a']++; }
    return ret;
  }

  vector<V> series;
  series.eb(a);
  series.eb(Count(S));
  int idx = 1;
  while (1) {
    if (Sum(series[idx]) * 2 >= r) {
      assert(Sum(series[idx]) < r);
      {
        ret = series[idx];
        r -= Sum(series[idx]);
      }
      break;
    }

    series.eb();
    rep(i, 26) { series.back()[i] = series[idx - 1][i] + series[idx][i]; }
    ++idx;
  }

  while (idx > 1) {
    // cout << "r: " << r << endl;
    // cout << idx << ": ";
    // rep(i, 26) {
    //   if (i) cout << " ";
    //   cout << ret[i];
    // }cout << endl;
    assert(Sum(series[idx]) >= r);
    --idx;
    if (Sum(series[idx]) <= r) {
      rep(i, 26) ret[i] += series[idx][i];
      r -= Sum(series[idx]);
      --idx;
    }
  }
  if (idx == 1) {
    assert(r <= S.size());
    rep(i, r) { ret[S[i] - 'a']++; }
  } else {
    assert(idx == 0 && Sum(series[idx]) >= r);
    assert(r <= w);
    rep(i, r) { ret[P[i] - 'a']++; }
  }
  return ret;
}

signed main() {
  ios_base::sync_with_stdio(false);
  cout << fixed << setprecision(0);

  cin >> S;
  assert(S.size() % 2 == 0);
  S = S.substr(S.size() / 2);
  cin >> L >> R;
  auto ans = Solve(R);
  auto sub = Solve(L - 1);
  rep(i, 26) {
    if (i)
      cout << " ";
    assert(ans[i] >= sub[i]);
    cout << ans[i] - sub[i];
  }
  cout << endl;
}