Problem p02588 (C++) — buggy submission, verdict: Runtime Error

#ifdef LOCAL
#define _GLIBCXX_DEBUG
#define __clock__
#else
#pragma GCC optimize("Ofast")
#endif
#include <bits/stdc++.h>
using namespace std;
using ll = long long;
using ld = long double;
using VI = vector<ll>;
using VV = vector<VI>;
using VS = vector<string>;
using PII = pair<ll, ll>;

// tourist set
template <typename A, typename B> string to_string(pair<A, B> p);

template <typename A, typename B, typename C>
string to_string(tuple<A, B, C> p);

template <typename A, typename B, typename C, typename D>
string to_string(tuple<A, B, C, D> p);

string to_string(const string &s) { return '"' + s + '"'; }

string to_string(const char *s) { return to_string((string)s); }

string to_string(bool b) { return (b ? "true" : "false"); }

string to_string(vector<bool> v) {
  bool first = true;
  string res = "{";
  for (int i = 0; i < static_cast<int>(v.size()); i++) {
    if (!first) {
      res += ", ";
    }
    first = false;
    res += to_string(v[i]);
  }
  res += "}";
  return res;
}

template <size_t N> string to_string(bitset<N> v) {
  string res = "";
  for (size_t i = 0; i < N; i++) {
    res += static_cast<char>('0' + v[i]);
  }
  return res;
}

template <typename A> string to_string(A v) {
  bool first = true;
  string res = "{";
  for (const auto &x : v) {
    if (!first) {
      res += ", ";
    }
    first = false;
    res += to_string(x);
  }
  res += "}";
  return res;
}

template <typename A, typename B> string to_string(pair<A, B> p) {
  return "(" + to_string(p.first) + ", " + to_string(p.second) + ")";
}

template <typename A, typename B, typename C>
string to_string(tuple<A, B, C> p) {
  return "(" + to_string(get<0>(p)) + ", " + to_string(get<1>(p)) + ", " +
         to_string(get<2>(p)) + ")";
}

template <typename A, typename B, typename C, typename D>
string to_string(tuple<A, B, C, D> p) {
  return "(" + to_string(get<0>(p)) + ", " + to_string(get<1>(p)) + ", " +
         to_string(get<2>(p)) + ", " + to_string(get<3>(p)) + ")";
}

void debug_out() { cerr << '\\n'; }

template <typename Head, typename... Tail> void debug_out(Head H, Tail... T) {
  cerr << " " << to_string(H);
  debug_out(T...);
}

#ifdef LOCAL
#define debug(...) cerr << "[" << #__VA_ARGS__ << "]:", debug_out(__VA_ARGS__)
#else
#define debug(...) 42
#endif
// tourist set end

template <class T> bool chmax(T &a, const T &b) {
  if (a < b) {
    a = b;
    return 1;
  }
  return 0;
}
template <class T> bool chmin(T &a, const T &b) {
  if (b < a) {
    a = b;
    return 1;
  }
  return 0;
}

#define FOR(i, a, b) for (ll i = (a); i < (b); ++i)
#define rep(i, b) FOR(i, 0, b)
#define ALL(v) (v).begin(), (v).end()
#define p(s) cout << (s) << '\\n'
#define p2(s, t) cout << (s) << " " << (t) << '\\n'
#define br() p("")
#define pn(s) cout << (#s) << " " << (s) << '\\n'
#define SZ(x) ((int)(x).size())
#define SORT(A) sort(ALL(A))
#define RSORT(A) sort(ALL(A), greater<ll>())
#define MP make_pair
#define p_yes() p("YES")
#define p_no() p("NO")

ll SUM(VI &V) { return accumulate(ALL(V), 0LL); }

ll MIN(VI &V) { return *min_element(ALL(V)); }
ll MAX(VI &V) { return *max_element(ALL(V)); }

void print_vector(VI &V) {
  ll n = V.size();
  rep(i, n) {
    if (i)
      cout << ' ';
    cout << V[i];
  }
  cout << endl;
}

ll gcd(ll a, ll b) {
  if (b == 0)
    return a;
  return gcd(b, a % b);
}

ll lcm(ll a, ll b) {
  ll g = gcd(a, b);
  return a / g * b;
}

// long double
using ld = long double;
#define EPS (1e-14)
#define equals(a, b) (fabs((a) - (b)) < EPS)

void no() {
  p_no();
  exit(0);
}
void yes() {
  p_yes();
  exit(0);
}

const ll mod = 1e9 + 7;
const ll inf = 1e18;
const double PI = acos(-1);

// snuke's mint
// auto mod int
// https://youtu.be/L8grWxBlIZ4?t=9858
// https://youtu.be/ERZuLAxZffQ?t=4807 : optimize
// https://youtu.be/8uowVvQ_-Mo?t=1329 : division
// const int mod = 1000000007;
struct mint {
  ll x; // typedef long long ll;
  mint(ll x = 0) : x((x % mod + mod) % mod) {}
  mint operator-() const { return mint(-x); }
  mint &operator+=(const mint a) {
    if ((x += a.x) >= mod)
      x -= mod;
    return *this;
  }
  mint &operator-=(const mint a) {
    if ((x += mod - a.x) >= mod)
      x -= mod;
    return *this;
  }
  mint &operator*=(const mint a) {
    (x *= a.x) %= mod;
    return *this;
  }
  mint operator+(const mint a) const {
    mint res(*this);
    return res += a;
  }
  mint operator-(const mint a) const {
    mint res(*this);
    return res -= a;
  }
  mint operator*(const mint a) const {
    mint res(*this);
    return res *= a;
  }
  mint pow(ll t) const {
    if (!t)
      return 1;
    mint a = pow(t >> 1);
    a *= a;
    if (t & 1)
      a *= *this;
    return a;
  }

  // for prime mod
  mint inv() const { return pow(mod - 2); }
  mint &operator/=(const mint a) { return (*this) *= a.inv(); }
  mint operator/(const mint a) const {
    mint res(*this);
    return res /= a;
  }
};

// vをaでなんかい割れるか
ll f(ll v, ll a) {
  ll cnt = 0;
  while (v % a == 0) {
    v /= a;
    cnt++;
  }
  return cnt;
}

// 2次元累積和
struct AccSum2D {
  VV Ac; // accumulate
  ll W;
  ll H;
  AccSum2D() {}
  AccSum2D(VV &A) {
    H = A.size();
    W = A[0].size();
    Ac.resize(H + 1, VI(W + 1));
    // indexを1つずらしてコピー
    rep(i, H) {
      rep(j, W) { Ac[i + 1][j + 1] = A[i][j]; }
    }
    // 横に累積
    rep(i, H + 1) {
      rep(j, W) { Ac[i][j + 1] += Ac[i][j]; }
    }
    // 縦に累積
    rep(x, W + 1) {
      rep(y, H) { Ac[y + 1][x] += Ac[y][x]; }
    }
  }
  // 入力したAの0-indexで指定 (閉区間)
  // sum of (a,b) to (c,d)
  // a, cはy方向
  // b, dはx方向
  ll sum(ll a, ll b, ll c, ll d) {
    if (a < 0)
      a = 0;
    if (b < 0)
      b = 0;
    if (c < 0)
      c = 0;
    if (d < 0)
      d = 0;
    // 内部ではindexが1ずれる
    a++;
    b++;
    c++;
    d++;
    return Ac[c][d] - Ac[a - 1][d] - Ac[c][b - 1] + Ac[a - 1][b - 1];
  }
};

vector<string> split_str(string s, char c) {
  vector<string> ret;
  stringstream ss;
  FOR(i, 0, s.size()) {
    if (s[i] == c) {
      ret.push_back(ss.str());
      ss.str("");
      ss.clear();
    } else {
      ss << s[i];
    }
  }
  ret.push_back(ss.str());
  return ret;
}

ll get_from_str() {
  string s;
  cin >> s;
  if (s.find(".") == string::npos) {
    s += ".000000000000";
  } else {
    s += "00000000000";
  }
  debug(s);
  // 10e9倍
  ll dot = s.find(".");
  FOR(i, dot, dot + 9) { swap(s[i], s[i + 1]); }
  // ドット以下除去
  return stoll(split_str(s, '.')[0]);
}

int main() {
  cin.tie(0);
  ios::sync_with_stdio(false);

  // input
  ll N;
  cin >> N;

  VI A(N);
  rep(i, N) {
    // ld a;cin>>a;
    // A[i] = 1e9 * a;
    A[i] = get_from_str();
  }

  debug(A);

  VI B(N);
  rep(i, N) {
    ll a = A[i];
    B[i] = f(a, 2);
  }

  VI C(N);
  rep(i, N) {
    ll a = A[i];
    C[i] = f(a, 5);
  }

  debug(B);
  debug(C);

  // ll cnt=0;
  // rep(i,N){
  //   FOR(j,i+1,N){
  //     if(B[i]+B[j]>=18 && C[i]+C[j]>=18) cnt++;
  //   }
  // }
  // p(cnt);

  VV G(100, VI(100));
  rep(i, N) {
    ll b = B[i];
    ll c = C[i];
    G[b][c]++;
  }
  auto Acc = AccSum2D(G);

  ll sum = 0;
  rep(i, N) {
    ll b = B[i];
    ll c = C[i];

    sum += Acc.sum(18 - b, 18 - c, 50, 50);
  }

  rep(i, N) {
    ll b = B[i];
    ll c = C[i];
    if (2 * b >= 18 && 2 * c >= 18)
      sum--;
  }
  p(sum / 2);

  return 0;
}

Error: WA

Fixed submission:

#ifdef LOCAL
#define _GLIBCXX_DEBUG
#define __clock__
#else
#pragma GCC optimize("Ofast")
#endif
#include <bits/stdc++.h>
using namespace std;
using ll = long long;
using ld = long double;
using VI = vector<ll>;
using VV = vector<VI>;
using VS = vector<string>;
using PII = pair<ll, ll>;

// tourist set
template <typename A, typename B> string to_string(pair<A, B> p);

template <typename A, typename B, typename C>
string to_string(tuple<A, B, C> p);

template <typename A, typename B, typename C, typename D>
string to_string(tuple<A, B, C, D> p);

string to_string(const string &s) { return '"' + s + '"'; }

string to_string(const char *s) { return to_string((string)s); }

string to_string(bool b) { return (b ? "true" : "false"); }

string to_string(vector<bool> v) {
  bool first = true;
  string res = "{";
  for (int i = 0; i < static_cast<int>(v.size()); i++) {
    if (!first) {
      res += ", ";
    }
    first = false;
    res += to_string(v[i]);
  }
  res += "}";
  return res;
}

template <size_t N> string to_string(bitset<N> v) {
  string res = "";
  for (size_t i = 0; i < N; i++) {
    res += static_cast<char>('0' + v[i]);
  }
  return res;
}

template <typename A> string to_string(A v) {
  bool first = true;
  string res = "{";
  for (const auto &x : v) {
    if (!first) {
      res += ", ";
    }
    first = false;
    res += to_string(x);
  }
  res += "}";
  return res;
}

template <typename A, typename B> string to_string(pair<A, B> p) {
  return "(" + to_string(p.first) + ", " + to_string(p.second) + ")";
}

template <typename A, typename B, typename C>
string to_string(tuple<A, B, C> p) {
  return "(" + to_string(get<0>(p)) + ", " + to_string(get<1>(p)) + ", " +
         to_string(get<2>(p)) + ")";
}

template <typename A, typename B, typename C, typename D>
string to_string(tuple<A, B, C, D> p) {
  return "(" + to_string(get<0>(p)) + ", " + to_string(get<1>(p)) + ", " +
         to_string(get<2>(p)) + ", " + to_string(get<3>(p)) + ")";
}

void debug_out() { cerr << '\\n'; }

template <typename Head, typename... Tail> void debug_out(Head H, Tail... T) {
  cerr << " " << to_string(H);
  debug_out(T...);
}

#ifdef LOCAL
#define debug(...) cerr << "[" << #__VA_ARGS__ << "]:", debug_out(__VA_ARGS__)
#else
#define debug(...) 42
#endif
// tourist set end

template <class T> bool chmax(T &a, const T &b) {
  if (a < b) {
    a = b;
    return 1;
  }
  return 0;
}
template <class T> bool chmin(T &a, const T &b) {
  if (b < a) {
    a = b;
    return 1;
  }
  return 0;
}

#define FOR(i, a, b) for (ll i = (a); i < (b); ++i)
#define rep(i, b) FOR(i, 0, b)
#define ALL(v) (v).begin(), (v).end()
#define p(s) cout << (s) << '\\n'
#define p2(s, t) cout << (s) << " " << (t) << '\\n'
#define br() p("")
#define pn(s) cout << (#s) << " " << (s) << '\\n'
#define SZ(x) ((int)(x).size())
#define SORT(A) sort(ALL(A))
#define RSORT(A) sort(ALL(A), greater<ll>())
#define MP make_pair
#define p_yes() p("YES")
#define p_no() p("NO")

ll SUM(VI &V) { return accumulate(ALL(V), 0LL); }

ll MIN(VI &V) { return *min_element(ALL(V)); }
ll MAX(VI &V) { return *max_element(ALL(V)); }

void print_vector(VI &V) {
  ll n = V.size();
  rep(i, n) {
    if (i)
      cout << ' ';
    cout << V[i];
  }
  cout << endl;
}

ll gcd(ll a, ll b) {
  if (b == 0)
    return a;
  return gcd(b, a % b);
}

ll lcm(ll a, ll b) {
  ll g = gcd(a, b);
  return a / g * b;
}

// long double
using ld = long double;
#define EPS (1e-14)
#define equals(a, b) (fabs((a) - (b)) < EPS)

void no() {
  p_no();
  exit(0);
}
void yes() {
  p_yes();
  exit(0);
}

const ll mod = 1e9 + 7;
const ll inf = 1e18;
const double PI = acos(-1);

// snuke's mint
// auto mod int
// https://youtu.be/L8grWxBlIZ4?t=9858
// https://youtu.be/ERZuLAxZffQ?t=4807 : optimize
// https://youtu.be/8uowVvQ_-Mo?t=1329 : division
// const int mod = 1000000007;
struct mint {
  ll x; // typedef long long ll;
  mint(ll x = 0) : x((x % mod + mod) % mod) {}
  mint operator-() const { return mint(-x); }
  mint &operator+=(const mint a) {
    if ((x += a.x) >= mod)
      x -= mod;
    return *this;
  }
  mint &operator-=(const mint a) {
    if ((x += mod - a.x) >= mod)
      x -= mod;
    return *this;
  }
  mint &operator*=(const mint a) {
    (x *= a.x) %= mod;
    return *this;
  }
  mint operator+(const mint a) const {
    mint res(*this);
    return res += a;
  }
  mint operator-(const mint a) const {
    mint res(*this);
    return res -= a;
  }
  mint operator*(const mint a) const {
    mint res(*this);
    return res *= a;
  }
  mint pow(ll t) const {
    if (!t)
      return 1;
    mint a = pow(t >> 1);
    a *= a;
    if (t & 1)
      a *= *this;
    return a;
  }

  // for prime mod
  mint inv() const { return pow(mod - 2); }
  mint &operator/=(const mint a) { return (*this) *= a.inv(); }
  mint operator/(const mint a) const {
    mint res(*this);
    return res /= a;
  }
};

// vをaでなんかい割れるか
ll f(ll v, ll a) {
  ll cnt = 0;
  while (v % a == 0) {
    v /= a;
    cnt++;
  }
  return cnt;
}

// 2次元累積和
struct AccSum2D {
  VV Ac; // accumulate
  ll W;
  ll H;
  AccSum2D() {}
  AccSum2D(VV &A) {
    H = A.size();
    W = A[0].size();
    Ac.resize(H + 1, VI(W + 1));
    // indexを1つずらしてコピー
    rep(i, H) {
      rep(j, W) { Ac[i + 1][j + 1] = A[i][j]; }
    }
    // 横に累積
    rep(i, H + 1) {
      rep(j, W) { Ac[i][j + 1] += Ac[i][j]; }
    }
    // 縦に累積
    rep(x, W + 1) {
      rep(y, H) { Ac[y + 1][x] += Ac[y][x]; }
    }
  }
  // 入力したAの0-indexで指定 (閉区間)
  // sum of (a,b) to (c,d)
  // a, cはy方向
  // b, dはx方向
  ll sum(ll a, ll b, ll c, ll d) {
    // 内部ではindexが1ずれる
    a++;
    b++;
    c++;
    d++;
    return Ac[c][d] - Ac[a - 1][d] - Ac[c][b - 1] + Ac[a - 1][b - 1];
  }
};

int main() {
  cin.tie(0);
  ios::sync_with_stdio(false);

  // input
  ll N;
  cin >> N;

  VI A(N);
  rep(i, N) {
    ld a;
    cin >> a;
    A[i] = 1e9 * a;
  }

  debug(A);

  VI B(N);
  rep(i, N) {
    ll a = A[i];
    B[i] = f(a, 2);
  }

  VI C(N);
  rep(i, N) {
    ll a = A[i];
    C[i] = f(a, 5);
  }

  debug(B);
  debug(C);

  // ll cnt=0;
  // rep(i,N){
  //   FOR(j,i+1,N){
  //     if(B[i]+B[j]>=18 && C[i]+C[j]>=18) cnt++;
  //   }
  // }
  // p(cnt);

  VV G(100, VI(100));
  rep(i, N) {
    ll b = B[i];
    ll c = C[i];
    G[b][c]++;
  }
  auto Acc = AccSum2D(G);

  ll sum = 0;
  rep(i, N) {
    ll b = B[i];
    ll c = C[i];

    sum += Acc.sum(18 - b, 18 - c, 50, 50);
  }

  rep(i, N) {
    ll b = B[i];
    ll c = C[i];
    if (2 * b >= 18 && 2 * c >= 18)
      sum--;
  }
  p(sum / 2);

  return 0;
}